2013-05-07 5 views
0

У меня есть рамка данных pandas, как показано ниже. Я хочу, чтобы получить список «Job_No» для всех комбинаций («user_id», «Exec_No»)группировка в кадре данных pandas

User_ID Exec_No Job_No 
1: 2  1  1 
2: 2  2  2 
3: 3  2  3 
4: 1  2  4 
5: 1  1  5 
6: 3  2  6 
7: 2  2  7 
8: 1  1  8 

Нужный выход другой кадр данных, который выглядит как

User_ID Exec_No Job_No 
1: 2  1  [1] 
2: 2  2  [2,7] 
3: 3  2  [3,6] 
4: 1  2  [4] 
5: 1  1  [5,8] 

Как Я делаю это, используя несколько строк кода?

Также ожидается, что в кадре данных будет около миллиона строк. Поэтому производительность также важна.

ответ

0

Решение прямолинейно.

говорят, что если 'DF' является объектом dataframe, то

grp_df = df.groupby(['User_ID','Exec_No']) 
newdf = grp_df['Job_No'] 
+0

Параметр 'grp_df' это «объект GroupBy», а не DataFrame. Выбор столбца из него снова возвращает объект Groupby, поэтому вам все равно нужно сделать что-то вроде 'grp_df ['Job_No']. Apply (lambda x: x.values)'. –

0

Это даст серию в ответ:

df.groupby(['User_ID', 'Exec_No']).apply(lambda x: x.Job_No.values) 

Подведем в серии в применяются возвращает DataFrame:

df.groupby(['User_ID', 'Exec_No']).apply(lambda x: pd.Series([x.Job_No.values])) 

User_ID Exec_No   
1  1  [5, 8] 
     2   [4] 
2  1   [1] 
     2  [2, 7] 
3  2  [3, 6] 

Было бы неплохо, если бы name= серии использовались в качестве результирующей колонки na меня, но это не так.

2

В качестве примечания, если вы заботитесь о производительности, хранение списков в DataFrame не очень эффективно. После группировки данных сразу можно получить доступ к значениям Job_No, не нужно создавать новые списки хранения данных DataFrame (память!) Из пары Job_No per (User_Id, Exec_No).

In [21]: df 
Out[21]: 
    User_ID Exec_No Job_No 
0  2  1  1 
1  2  2  2 
2  3  2  3 
3  1  2  4 
4  1  1  5 
5  3  2  6 
6  2  2  7 
7  1  1  8 

In [22]: grouped = df.groupby(['User_ID', 'Exec_No']) 

In [23]: grouped.get_group((3, 2)) 
Out[23]: 
    User_ID Exec_No Job_No 
2  3  2  3 
5  3  2  6 

In [24]: grouped.get_group((3, 2))['Job_No'] 
Out[24]: 
2 3 
5 6 
Name: Job_No, dtype: int64 

In [25]: list(grouped.get_group((3, 2))['Job_No']) 
Out[25]: [3, 6] 
0

Как об этом способе:

df = pd.DataFrame({'User_ID' : [2,2, 3, 1, 1, 3, 2, 1], 'Exec_No': [1, 2, 2, 2, 1, 2, 2, 1], 'Job_No':[1,2,3,4,5,6,7,8]}, columns=['User_ID', 'Exec_No','Job_No']) 

df 
User_ID Exec_No Job_No 
0 2 1 1 
1 2 2 2 
2 3 2 3 
3 1 2 4 
4 1 1 5 
5 3 2 6 
6 2 2 7 
7 1 1 8 

Давайте делать группу по:

df2 = df.groupby(['User_ID', 'Exec_No'], sort=False).apply(lambda x: list(x['Job_No'])) 
df2  
User_ID Exec_No 
2  1    [1] 
     2   [2, 7] 
3  2   [3, 6] 
1  1   [5, 8] 
     2    [4] 

и поставить так, как вы хотели его:

df2.reset_index() 

User_ID Exec_No 0 
0 2 1 [1] 
1 2 2 [2, 7] 
2 3 2 [3, 6] 
3 1 1 [5, 8] 
4 1 2 [4] 
Смежные вопросы