Groupby для создания новых столбцов - PullRequest
0 голосов
/ 13 декабря 2018

Из фрейма данных я хочу создать фрейм данных с новыми столбцами, если индекс уже найден, НО я не знаю, сколько столбцов я создам:

pd.DataFrame([["John","guitar"],["Michael","football"],["Andrew","running"],["John","dancing"],["Andrew","cars"]])

и я хочу:

pd.DataFrame([["John","guitar","dancing"],["Michael","Football",None],["Andrew","running","cars"]])

, не зная, сколько столбцов я должен создать в начале.

Ответы [ 3 ]

0 голосов
/ 13 декабря 2018
df = pd.DataFrame([["John","guitar"],["Michael","football"],["Andrew","running"],["John","dancing"],["Andrew","cars"]], columns = ['person','hobby'])

Вы можете группировать person и искать unique в hobby.Затем используйте .apply(pd.Series), чтобы развернуть списки в столбцы:

df.groupby('person').hobby.unique().apply(pd.Series).reset_index()
    person         0        1
0   Andrew   running     cars
1     John    guitar  dancing
2  Michael  football      NaN

В случае большого фрейма данных попробуйте более эффективную альтернативу:

df = df.groupby('person').hobby.unique()
df = pd.DataFrame(df.values.tolist(), index=df.index).reset_index()

Что по сути делает то же самое, но избегает зацикливания строк при применении pd.Series.

0 голосов
/ 13 декабря 2018

Предполагая, что имена столбцов ['person', 'activity'], вы можете сделать

df_out = df.groupby('person').agg(list).reset_index()
df_out = pd.concat([df_out, pd.DataFrame(df_out['activity'].values.tolist())], axis=1)
df_out = df_out.drop('activity', 1)

, давая вам

    person         0        1
0   Andrew   running     cars
1     John    guitar  dancing
2  Michael  football     None
0 голосов
/ 13 декабря 2018

Используйте GroupBy.cumcount для получения counter, а затем измените форму на unstack:

df1 = pd.DataFrame([["John","guitar"],
                    ["Michael","football"],
                    ["Andrew","running"],
                    ["John","dancing"],
                    ["Andrew","cars"]], columns=['a','b'])

         a         b
0     John    guitar
1  Michael  football
2   Andrew   running
3     John   dancing
4   Andrew      cars


df = (df1.set_index(['a', df1.groupby('a').cumcount()])['b']
         .unstack()
         .rename_axis(-1)
         .reset_index()
         .rename(columns=lambda x: x+1))
print (df)

         0         1        2
0   Andrew   running     cars
1     John    guitar  dancing
2  Michael  football      NaN

Или объедините list и создайте новый словарьпо конструктору:

s = df1.groupby('a')['b'].agg(list)
df = pd.DataFrame(s.values.tolist(), index=s.index).reset_index()
print (df)
         a         0        1
0   Andrew   running     cars
1     John    guitar  dancing
2  Michael  football     None
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...