Python - Выполнение Макс функции на нескольких групповых - PullRequest
0 голосов
/ 07 ноября 2018

Ниже у меня есть данные, показывающие цены на дерево и сталь от двух разных поставщиков.

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

Например, в строке «Сталь» для «Тома» будет показана его самая высокая цена на древесину - 42.

Код, который у меня есть, просто возвращает самую высокую цену за оригинальный предмет (т.е. не наоборот, поэтому для стального ряда Тома возвращается 24, но я бы хотел, чтобы он возвратил 42).

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

Любые мысли будут с благодарностью.

import pandas as pd
import numpy as np
data = {'Supplier':['Tom', 'Tom', 'Tom', 'Bill','Bill','Bill'],'Item':['Wood','Wood','Steel','Steel','Steel','Wood'],'Price':[42,33,24,16,12,18]}
df = pd.DataFrame(data)

df['Opp_Item'] = np.where(df['Item']=="Wood", "Steel", "Wood")
df['Opp_Item_Max'] = df.groupby(['Supplier','Opp_Item'])['Price'].transform(max)
print(df)


  Supplier   Item  Price Opp_Item  Opp_Item_Max
0      Tom   Wood     42    Steel            42
1      Tom   Wood     33    Steel            42
2      Tom  Steel     24     Wood            24
3     Bill  Steel     16     Wood            16
4     Bill  Steel     12     Wood            16
5     Bill   Wood     18    Steel            18

Ответы [ 2 ]

0 голосов
/ 07 ноября 2018

Вы можете map перейти к противоположным значениям до группировки, а затем объединить это обратно с исходным кадром данных.

d = {'Steel': 'Wood', 'Wood': 'Steel'}

df.merge(df.assign(Item = df.Item.map(d))
           .groupby(['Supplier', 'Item'], as_index=False).max(),
         on=['Supplier', 'Item'],  
         how='left',
         suffixes=['', '_Opp_Item'])

  Supplier   Item  Price  Price_Opp_Item
0      Tom   Wood     42              24
1      Tom   Wood     33              24
2      Tom  Steel     24              42
3     Bill  Steel     16              18
4     Bill  Steel     12              18
5     Bill   Wood     18              16
0 голосов
/ 07 ноября 2018

Если вы можете найти максимум для каждого поставщика + элемент, то вы можете просто поменять значения и присвоить их обратно через join:

v = df.groupby(['Supplier', 'Item']).Price.max().unstack(-1)
# This reversal operation works under the assumption that
# there are only two items and that they are opposites of each other. 
v[:] = v.values[:, ::-1]  

df = (df.set_index(['Supplier', 'Item'])
        .join(v.stack().to_frame('Opp_Item_Max'), how='left')
        .reset_index())

print(df)
  Supplier   Item  Price  Opp_Item_Max
0     Bill  Steel     16            18
1     Bill  Steel     12            18
2     Bill   Wood     18            16
3      Tom  Steel     24            42
4      Tom   Wood     42            24
5      Tom   Wood     33            24

Примечание: порядок ваших данных не будет сохранен после объединения.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...