我有一个数据框,每个日期我想计算每个日期每个股票的销售绝对变化总和。
示例df:
Stock Sales Data 1
1/1/2012 Amazon 120 0.996691907
1/1/2012 Apple 230 0.084699221
1/1/2012 Microsoft 340 0.141253424
1/1/2012 Google 230 0.506264018
1/2/2012 Amazon 340 0.646633737
1/2/2012 Apple 1250 0.204030887
1/2/2012 Microsoft 850 0.556935133
1/2/2012 Dell 650 0.771751177
1/2/2012 Yahoo 650 0.615222763
1/2/2012 Verizon 1065 0.504410742
1/2/2012 Vodafone 200 0.752335341
1/2/2012 Blackberry 1465 0.693017964
1/2/2012 AT&T 2000 0.262392424
1/3/2012 Apple 1465 0.851841806
1/3/2012 Amazon 1465 0.70635569
1/3/2012 AT&T 700 0.911297224
1/3/2012 Blackberry 235 0.118843588
1/3/2012 Vodafone 500 0.07255267
输出df_new将是:
1/1/2012 920
1/2/2012 7780
1/3/2012 11050
计算:
对于 1/1/2012 (索引中的第一个日期),计算将只是当天销售额的总和(120 + 230 + 340 + 230)= 920
对于 1/2/2012 (下一个日期),计算将是日期变更期间特定股票的销售额的绝对变化。 例如,亚马逊,苹果和微软已经处于第一个日期,其余的股票都是新的,所以绝对变化的总和将是: (abs(340-120)+ abs(1250-230)+ abs(850-340)+ abs(650-0)+ abs(650-0)+ abs(1065-0)+ abs(200-0)+ abs(1465-0)+ abs(2000-0))= 7780。 由于戴尔,雅虎,Verizon,Vodafone,Blackberry,AT& T都是新的,并且在计算前一天不是简单的销售额减去0(因为他们前一天不在那里测量绝对变化)。
1/3/2012 (下一个日期)。计算如下: abs(1465-1250)+ abs(1465-340)+ abs(700-2000)+ abs(235-1465)+ abs(500-20)+ abs(0-1065)+ abs(0-650)+ abs (0-650)-abs(0-850)= 11050 由于微软,戴尔,雅虎和Verizon都是前一个日期而不是当前日期,因此它们的销量为0。
数据集很大,我试图找到一个可以完成所有这些操作的简单代码。数据涉及可能发生剧烈变化的股票,并且可能存在从一个日期到另一个日期没有股票的情况。
答案 0 :(得分:1)
在熊猫中你可以这样做:
>>> df
Stock Sales Data
1/1/2012 Amazon 120 0.996692
1/1/2012 Apple 230 0.084699
1/1/2012 Microsoft 340 0.141253
1/1/2012 Google 230 0.506264
...
>>> df2 = df.pivot(columns='Stock', values='Sales').fillna(0)
>>> df2
Stock AT&T Amazon Apple Blackberry Dell Google Microsoft Verizon Vodafone Yahoo
1/1/2012 0.0 120.0 230.0 0.0 0.0 230.0 340.0 0.0 0.0 0.0
1/2/2012 2000.0 340.0 1250.0 1465.0 650.0 0.0 850.0 1065.0 200.0 650.0
1/3/2012 700.0 1465.0 1465.0 235.0 0.0 0.0 0.0 0.0 500.0 0.0
>>> df3 = df2.diff().fillna(df2).abs()
>>> df3
Stock AT&T Amazon Apple Blackberry Dell Google Microsoft Verizon Vodafone Yahoo
1/1/2012 0.0 120.0 230.0 0.0 0.0 230.0 340.0 0.0 0.0 0.0
1/2/2012 2000.0 220.0 1020.0 1465.0 650.0 230.0 510.0 1065.0 200.0 650.0
1/3/2012 1300.0 1125.0 215.0 1230.0 650.0 0.0 850.0 1065.0 300.0 650.0
>>> df3.sum(axis=1)
1/1/2012 920.0
1/2/2012 8010.0
1/3/2012 7385.0
dtype: float64
注意:由于OP的计算错误,我得不到同样的结果 - 谷歌似乎从1/2中失踪了,计算只是1/3的错误。
答案 1 :(得分:0)
它更像是伪代码而我没有测试它但它或多或少应该是这样的:
prev_sales = {}
last_sales = {}
last_date = rows[0].date
for row in rows:
if row.date > last_date:
res = 0
for key, value in last_sales.iteritems():
res += abs(value - prev_sales.get(key, 0))
print last_date, res
last_date = row.date
prev_sales = last_sales
last_sales = {}
last_sales[row.stock] += last_sales.get(row.stock, 0)
时间复杂度是O(行数+天数*不同公司的数量),如果大多数公司每天都出现O(行数)。