我有一个包含交易的数据框。索引是事务的日期(时间戳),列是价格(浮点数),城市(字符串)和产品名称(字符串)。我想在数据框中添加一个新列,其中包含每个城市中每种产品的最低价格。因此,第四列对于城市和产品相同的每一行都具有相同的值。
以下是示例代码:
# dictionary of transactions
d = {'1': ['20', 'NYC', 'Widget A'], '2': ['30', 'NYC', 'Widget A'], '3': ['5', 'NYC', 'Widget A'], \
'4': ['300', 'LA', 'Widget B'], '5': ['30', 'LA', 'Widget B'], '6': ['100', 'LA', 'Widget A']}
columns=['Price', 'City', 'Product']
# create dataframe and rename columns
df = pd.DataFrame.from_dict(data=d, orient='index')
df.columns = columns
这会产生一个看起来像这样的数据框
Price City Product
1 20 NYC Widget A
2 30 NYC Widget A
3 5 NYC Widget A
4 300 LA Widget B
5 30 LA Widget B
6 100 LA Widget A
所以我想为每个城市/产品子组添加一个具有最低价格的新列。所以第1-3行(所有NYC / Widget A)将是5(第3行中的最低价格),第4行和第5行的值为30(LA / Widget B),第6行将具有价值100。
答案 0 :(得分:4)
从示例数据框product.csv
开始,如下所示:
date,price,city,product
2015-09-21,1.5,c1,p1
2015-09-21,1.2,c1,p1
2015-09-21,0.5,c1,p2
2015-09-21,0.3,c1,p2
2015-09-22,0.6,c2,p2
2015-09-22,1.2,c2,p2
我会这样做:
# Read Dataframe
df = pd.read_csv('product.csv')
然后我添加了所需的列:
df['minprice'] = df.groupby(['city','product'])['price'].transform(min)
返回:
date price city product minprice
0 2015-09-21 1.5 c1 p1 1.2
1 2015-09-21 1.2 c1 p1 1.2
2 2015-09-21 0.5 c1 p2 0.3
3 2015-09-21 0.3 c1 p2 0.3
4 2015-09-22 0.6 c2 p2 0.6
5 2015-09-22 1.2 c2 p2 0.6
希望有所帮助。
答案 1 :(得分:3)
您需要将transform
应用于groupby
,这会保留原始数据框的形状。
import pandas as pd
import numpy as np
df = pd.DataFrame({'price': np.round(np.random.random(15), 2),
'product': list('ABC') * 5,
'city': ['San Francisco'] * 10 + ['New York'] * 5}
df['min_city_product_price'] = df.groupby(['city', 'product']).price.transform(min)
>>> df
city price product min_city_product_price
0 San Francisco 0.65 A 0.35
1 San Francisco 0.97 B 0.28
2 San Francisco 0.09 C 0.09
3 San Francisco 0.35 A 0.35
4 San Francisco 0.28 B 0.28
5 San Francisco 0.84 C 0.09
6 San Francisco 0.49 A 0.35
7 San Francisco 0.94 B 0.28
8 San Francisco 0.13 C 0.09
9 San Francisco 0.89 A 0.35
10 New York 0.75 B 0.30
11 New York 0.31 C 0.31
12 New York 0.22 A 0.22
13 New York 0.30 B 0.30
14 New York 0.56 C 0.31