熊猫按多列分组,并保留所有其他列

时间:2020-04-22 16:34:09

标签: python pandas dataframe

我有一个df,它是两个结构相同的df的concat,第一个是Orders,第二个是CancelsOrders中有20,000多行,而少数Cancels中有相应的OrderNoItemCode。我将取消的数量设为负数,因此在将df按OrderNoItemCode分组时,我可以将数量字段与agg求和,从而为我提供实际的发货数量,以补偿取消的订单。

下面是我的数据框:

    OrderNo     OrderDate   LineNo  ClientNo    ItemCode    QtyOrdered  QtyShipped
0   528758  1/3/2017    1   1358538     111931  70  70
1   528791  1/3/2017    10  1254798     110441  300     300
2   528791  1/3/2017    1   1254798     1029071     10  10
3   528791  1/3/2017    2   1254798     1033341     10  10
4   528791  1/3/2017    8   1254798     1040726     15  15
...     ...     ...     ...     ...     ...     ...     ...
28344   537667  2/6/2017    12  43823870    10137992    0   -2
28345   537771  2/7/2017    5   1276705     1041106     0   -4
28346   539524  2/13/2017   6   1254798     1038323     0   -10
28347   542362  2/23/2017   11  1254612     1041108     0   -2
28348   542835  2/23/2017   13  1255235     10137993    0   -5

28349 rows × 7 columns

运行后:

ActualOrders = PreActualOrders.groupby(['OrderNo','ItemCode']).agg({'QtyOrdered': 'sum', 'QtyShipped': 'sum'}).reset_index()

我得到了想要的结果,但是我丢失了DF中的所有其他列。

下面的结果示例:

    OrderNo     ItemCode    QtyOrdered  QtyShipped
28255   543734  1038324     1   1
28256   543734  10137992    1   1
28257   543734  10137993    1   1
28258   543735  1041106     1   1
28259   543735  1041108     1   1
28260   543735  10135359    1   1

我需要添加什么以将所有列保留在原始df中?

那些其他列中的所有值都匹配,因为它们是对应的取消或顺序。

谢谢

MTH

2 个答案:

答案 0 :(得分:0)

如果我对您的理解正确,则可以在没有groupby的情况下尝试另一种方法。 与此类似:

orders = [["123", "1", 10], ["1234", "2", 100], ["12345", "3", 15]]
cancels = [["123", "1", 10]]

df_orders = pd.DataFrame(orders, columns=["OrderNo", "ItemCode", "Amount"])
df_cancels = pd.DataFrame(cancels, columns=["OrderNo", "ItemCode", "Amount"])

merged = df_orders.merge(df_cancels, how="left", on=["OrderNo", "ItemCode"], suffixes=["_orders", "_cancels"])
merged["Amount_cancels"] = merged["Amount_cancels"].fillna(0)
print("Before substract cancels")
print(merged)

merged["Amount_orders"] = merged["Amount_orders"] - merged["Amount_cancels"]
print("After substract cancels")
print(merged)

答案 1 :(得分:0)

通过将其他列包含在agg中的'first'函数中,而'QtyOrdered'和'QtyShipped'受'sum'约束,我能够获得所需的结果。

ActualOrders = PreActualOrders.groupby(['OrderNo','ItemCode']).agg({'OrderDate': 'first', 'LineNo': 'first', 'ClientNo': 'first', 'QtyOrdered': 'sum', 'QtyShipped': 'sum' }).reset_index()

获得我想要的结果:

      OrderNo   ItemCode    OrderDate LineNo ClientNo QtyOrdered QtyShipped
28255   543734  1038324     2/27/2017   3   1254787     1   1
28256   543734  10137992    2/27/2017   1   1254787     1   1
28257   543734  10137993    2/27/2017   2   1254787     1   1
28258   543735  1041106     2/27/2017   4   1816460     1   1
28259   543735  1041108     2/27/2017   3   1816460     1   1
28260   543735  10135359    2/27/2017   2   1816460     1   1
28261   543735  10137993    2/27/2017   1   1816460     1   1

由于匹配取消的数量非常少,因此输出示例未显示订购数量和发货数量之间的任何差异。具有相应取消的行已正确调整。