对数据帧进行迭代,并根据一列的值在具有前一行值的新列中执行操作



我有一个小df的股票价格与他们的行动。我想计算拆分后股票的调整所有权金额(即,如果你拥有1000股,股票有2-1拆分,那么你的所有权变成2000股)。我想重复一下"股票分割"。列,如果值= 0,则乘以";owner &;"股票分割"否则保持最后一个数量前的分裂。我尝试了很多方法,但我不确定我在哪里出错-我确实认为逻辑是错误的,但不知道如何修复它。

import yfinance as yf
aapl = yf.Ticker("AAPL")
hist = aapl.history(start="2014-06-01")
hist["ownership"] = 1000

Open    High    Low Close   Volume  Dividends   Stock Splits    ownership
Date                                
2014-06-02  20.338966   20.366877   19.971301   20.168608   369350800   0.0 0.0 1000
2014-06-03  20.162511   20.492319   20.155774   20.453819   292709200   0.0 0.0 1000
2014-06-04  20.450610   20.785872   20.407940   20.687378   335482000   0.0 0.0 1000
2014-06-05  20.731655   20.833356   20.616479   20.768549   303805600   0.0 0.0 1000
2014-06-06  20.850357   20.893990   20.676150   20.711439   349938400   0.0 0.0 1000 

我的代码如下:

hist.loc[hist['Stock Splits']==0,'ownerAdj'] = hist['ownership'].shift(1)
hist.loc[hist['Stock Splits']!=0,'ownerAdj'] = hist['ownership'].shift(1) * hist['Stock Splits']

然而,我并不总是得到正确的数字,就像下面的例子一样,在2014-06-09苹果已经分裂(7比1),所以从2014-06-09到下一个日期它有另一个分裂,即2020-08-31,结果应该是7000,但我得到了分裂后的1000

Date    Open    High    Low Close   Volume  Dividends   Stock Splits    ownership   ownerAdj
0   2014-06-02  20.338964   20.366875   19.971299   20.168606   369350800   0.0 0.0 1000    NaN
1   2014-06-03  20.162515   20.492323   20.155778   20.453823   292709200   0.0 0.0 1000    1000.0
2   2014-06-04  20.450608   20.785870   20.407938   20.687376   335482000   0.0 0.0 1000    1000.0
3   2014-06-05  20.731645   20.833346   20.616470   20.768539   303805600   0.0 0.0 1000    1000.0
4   2014-06-06  20.850359   20.893992   20.676152   20.711441   349938400   0.0 0.0 1000    1000.0
5   2014-06-09  20.818268   21.083269   20.604921   21.042845   301660000   0.0 7.0 1000    7000.0
6   2014-06-10  21.274162   21.346027   21.013652   21.166365   251108000   0.0 0.0 1000    1000.0
7   2014-06-11  21.139424   21.280908   20.991204   21.078789   182724000   0.0 0.0 1000    1000.0

我试图运行循环,但我得到错误:

for i, row in hist.iterrows():
if row["Stock Splits"] == 0:
row["ownerAdj"] = row["ownership"].shift(1)
elif row["Stock Splits"] != 0:
row["ownerAdj"] = row["ownership"].shift(1) * row["Stock Splits"]
---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-51-2d94c5e86953> in <module>
1 for i, row in hist.iterrows():
2     if row["Stock Splits"] == 0:
----> 3         row["adjust2"] = row["ownership"].shift(1)
4     elif row["Stock Splits"] != 0:
5         row["adjust2"] = row["ownership"].shift(1) * row["Stock Splits"]
AttributeError: 'numpy.float64' object has no attribute 'shift'

你可以这样做矢量化

hist['ownership'] = 1000 * np.cumprod(np.maximum(hist["Stock Splits"], 1))

在部分:

# No split can be expressed as a 1.0 split (You get 1 for every 1).
# Assumes you don't have negative splits.
adj_split = np.maximum(hist["Stock Splits"], 1)  
# The multiple of the initial ownership at each day compared to the first.
cumsplit = np.cumprod(adj_split)
initial_ownership = 1000
hist["ownership"] = cumsplit * initial_ownership

最新更新