Pandas 将价格序列“指数化”到一个起始时间点(指数水平=100),数据帧为:P(i,t)/P(i)
我有一个pandas数据框,其中datetime是数据框的索引,我使用t=0进行简化,实际上有类似20170101 09:30:00的内容Pandas 将价格序列“指数化”到一个起始时间点(指数水平=100),数据帧为:P(i,t)/P(i),pandas,dataframe,arithmetic-expressions,scalar,Pandas,Dataframe,Arithmetic Expressions,Scalar,我有一个pandas数据框,其中datetime是数据框的索引,我使用t=0进行简化,实际上有类似20170101 09:30:00的内容 datetime Stock A Stock B t=0 5 20 t=1 6 30 t=2 8 25 t=3 4 20 我想返回: datetime Stock A Stock B
datetime Stock A Stock B
t=0 5 20
t=1 6 30
t=2 8 25
t=3 4 20
我想返回:
datetime Stock A Stock B
t=0 100 100
t=1 120 150
t=2 140 125
t=3 80 100
用数学术语:Indexi,t=Pi,t/Pi,0
我试过了
df_norm = df[0:] / df[0:1]
print(df_norm)
这给了我一个错误
edit1:我尝试了工作正常的选项3,但还不能尝试NaN,但至少它没有为pctchange导致的第一个obs创建NaN。我还想知道,在执行之后,我的datetime不再是集合索引,这很容易通过重新分配它来修复
现在我尝试将其包装到函数中,但我认为索引导致的问题实际上与我第一次尝试时的错误相同:
def norming(x):
return x.assign(**x.drop('datetime', 1).pipe(
lambda d: d.div(d.shift().bfill()).cumprod()))
edit2:如果我的列datetime是一个索引,即
df_norm.set_index(['datetime'], inplace = True)
但是,我会得到一个错误,我需要更改什么?选项1
选择2
选择3
好像
p=100/df.iloc[0,1:]
df.iloc[:,1:]*=p
df
Out[1413]:
datetime StockA StockB
0 t=0 100 100
1 t=1 120 150
2 t=2 160 125
3 t=3 80 100
比我的答案好得多@piRSquared更好,因为他也得到了回报率:-我的df.assign版本**df.drop'datetime',1.pipelambda d:d.divd.iloc[0]。mul100@piRSquared这太棒了,先生:-谢谢你们的回答!在选项1中,我看到了fillna,我的数据中不时会出现NaN,实际上我希望保留它。这也会影响其他解决方案吗?此外,如果不太费劲,您是否介意对代码进行评论?代码中有一些特定的部分和语法我并不真正理解。复活节快乐!
def idx_me(a):
a = np.asarray(a)
r = np.append(1, a[1:] / a[:-1])
return r.cumprod() * 100
df.assign(**df.drop('datetime', 1).apply(idx_me))
datetime Stock A Stock B
0 t=0 100.0 100.0
1 t=1 120.0 150.0
2 t=2 160.0 125.0
3 t=3 80.0 100.0
df.assign(**df.drop('datetime', 1).pipe(
lambda d: d.div(d.shift().bfill()).cumprod().mul(100)))
datetime Stock A Stock B
0 t=0 100.0 100.0
1 t=1 120.0 150.0
2 t=2 160.0 125.0
3 t=3 80.0 100.0
p=100/df.iloc[0,1:]
df.iloc[:,1:]*=p
df
Out[1413]:
datetime StockA StockB
0 t=0 100 100
1 t=1 120 150
2 t=2 160 125
3 t=3 80 100