Как получить верхние значения в каждой группе? - PullRequest
0 голосов
/ 03 мая 2020

Я новичок в Pandas, и у меня есть набор данных, который выглядит примерно так:

s_name  Time        p_name  qty
A       12/01/2019  ABC     1
A       12/01/2019  ABC     1
A       12/01/2019  DEF     2
A       12/01/2019  DEF     2
A       12/01/2019  FGH     0
B       13/02/2019  ABC     3
B       13/02/2019  DEF     1
B       13/02/2019  DEF     1
B       13/03/2019  ABC     3
B       13/03/2019  FGH     0

Я пытаюсь сгруппировать по s_name и найти сумму кол-во каждого уникального p_name в месяц, но отображать только p_name с двумя верхними значениями. Ниже приведен пример того, как я хочу, чтобы конечный результат выглядел следующим образом.

s_name  Time        p_name  qty
A       01          DEF     4
A       01          ABC     2
B       02          ABC     3
B       02          DEF     2
B       03          ABC     2
B       03          FGH     0

У вас есть идеи? Я застрял здесь довольно долго, поэтому очень ценю помощь.

Ответы [ 2 ]

1 голос
/ 03 мая 2020

Создайте month, используя dt, затем сгруппируйте по s_name и month, затем apply функцию для групп, сгруппируйте каждую группу по name и выполните sum над qty, sort_values по убыванию и получите только первые две строки с head:

df.Time = pd.to_datetime(df.Time, format='%d/%m/%Y')
df['month'] = df.Time.dt.month

df_f = df.groupby(['s_name', 'month']).apply(
    lambda df:
        df.groupby('p_name').qty.sum()
        .sort_values(ascending=False).head(2)
).reset_index()

df_f
#   s_name  month   p_name  qty
# 0 A   1   DEF 4
# 1 A   1   ABC 2
# 2 B   2   ABC 3
# 3 B   2   DEF 2
# 4 B   3   ABC 3
# 5 B   3   FGH 0
1 голос
/ 03 мая 2020

Я новичок в Pandas сам. Я попытаюсь ответить на ваш вопрос.

См. Этот код.

from io import StringIO
import pandas as pd

columns = "s_name Time p_name qty"

# Create dataframe from text.
df = pd.read_csv(
    StringIO(
        f"""{columns}
A 12/01/2019 ABC 1
A 12/01/2019 ABC 1
A 12/01/2019 DEF 2
A 12/01/2019 DEF 2
A 12/01/2019 FGH 0
B 13/02/2019 ABC 3
B 13/02/2019 DEF 1
B 13/02/2019 DEF 1
B 13/03/2019 ABC 3
B 13/03/2019 FGH 0"""
    ),
    sep=" ",
)


S_NAME, TIME, P_NAME, QTY = columns.split()
MONTH = "month"

# Convert the TIME col to datetime types.
df.Time = pd.to_datetime(df.Time, dayfirst=True)


# Create a month column with zfilled strings.
df[MONTH] = df.Time.apply(lambda x: str(x.month).zfill(2))


# Group
group = df.groupby(by=[S_NAME, P_NAME, MONTH])


gdf = (
    group.sum()
    .sort_index()
    .sort_values(by=[S_NAME, MONTH, QTY], ascending=False)
    .reset_index()
)

gdf.groupby([S_NAME, MONTH]).head(2).sort_values(by=[S_NAME, MONTH]).reset_index()

Это ожидаемый вами результат?

enter image description here

...