Панды - группировка и агрегирование по нескольким столбцам - PullRequest
2 голосов
/ 26 мая 2019

Я пытаюсь объединить значения в группу по нескольким столбцам.Я родом из мира R / dplyr, и то, что я хочу, обычно достигается в одной строке с помощью group_by / Summaze.Я пытаюсь найти такой же элегантный способ достижения этой цели с помощью панд.

Рассмотрим приведенный ниже набор входных данных.Я хотел бы агрегировать по состоянию и вычислить столбец v1 как v1 = сумма (n1) / сумма (d1) по состоянию .

Код r для этого с использованием dplyr выглядит следующим образом:

input %>% group_by(state) %>% 
  summarise(v1=sum(n1)/sum(d1),
            v2=sum(n2)/sum(d2))

Есть ли элегантный способ сделать это в Python?Я нашел немного подробный способ получить то, что я хочу, в ответе переполнения стека здесь .Копирование измененного Python-кода по ссылке

In [14]: s = mn.groupby('state', as_index=False).sum()

In [15]: s['v1'] = s['n1'] / s['d1']

In [16]: s['v2'] = s['n2'] / s['d2']
In [17]: s[['state', 'v1', 'v2']]

ВХОДНОЙ ДАННЫЙ

state n1    n2     d1  d2
CA   100   1000    1   2
FL   200   2000    2   4
CA   300   3000    3   6
AL   400   4000    4   8
FL   500   5000    5   2
NY   600   6000    6   4
CA   700   7000    7   6

ВЫХОД

state   v1           v2
AL      100   500.000000
CA      100   500.000000
NY      100  1500.000000
CA      100  1166.666667
FL      100  1166.666667

Ответы [ 2 ]

1 голос
/ 26 мая 2019

Другое решение:

def func(x):
    u = x.sum()
    return pd.Series({'v1':u['n1']/u['d1'],
                      'v2':u['n2']/u['d2']})

df.groupby('state').apply(func)

Вывод:

         v1     v2
state       
AL      100.0   500.000000
CA      100.0   785.714286
FL      100.0   1166.666667
NY      100.0   1500.000000
1 голос
/ 26 мая 2019

Одно возможное решение с DataFrame.assign и DataFrame.reindex:

df = (mn.groupby('state', as_index=False)
        .sum()
        .assign(v1 = lambda x: x['n1'] / x['d1'], v2 = lambda x: x['n2'] / x['d2'])
        .reindex(['state', 'v1', 'v2'], axis=1))

print (df)
  state     v1           v2
0    AL  100.0   500.000000
1    CA  100.0   785.714286
2    FL  100.0  1166.666667
3    NY  100.0  1500.000000

И еще один с GroupBy.apply и пользовательской лямбда-функцией:

df = (mn.groupby('state')
        .apply(lambda x: x[['n1','n2']].sum() / x[['d1','d2']].sum().values)
        .reset_index()  
        .rename(columns={'n1':'v1', 'n2':'v2'})
      )
print (df)
  state     v1           v2
0    AL  100.0   500.000000
1    CA  100.0   785.714286
2    FL  100.0  1166.666667
3    NY  100.0  1500.000000
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...