Python 计算价格变动及;基于另一列条件的价格累计百分比变化

Python 计算价格变动及;基于另一列条件的价格累计百分比变化,python,pandas,dataframe,Python,Pandas,Dataframe,问题的背景是,我正试图对交易策略进行回溯测试,并评估我的投资组合在一段时间内的表现。我正在使用Pandas DataFrame来处理数据 我已经使用 data = {'position': [1, 0, 0, 0, -1, 0, 0, 1, 0, 0], 'close': [10,25,30,25,22,20,21,16,11,20], 'close_position' : [10,25,30,25,22,22,22,16,11,20]} df = pd.D

问题的背景是,我正试图对交易策略进行回溯测试,并评估我的投资组合在一段时间内的表现。我正在使用Pandas DataFrame来处理数据

我已经使用

data = {'position': [1, 0, 0, 0, -1, 0, 0, 1, 0, 0], 
        'close': [10,25,30,25,22,20,21,16,11,20], 
        'close_position' : [10,25,30,25,22,22,22,16,11,20]}

df = pd.DataFrame(data = data)
输出df将是

+-------+----------+------------+----------------+
| index | position | close      | close_position |
+-------+----------+------------+----------------+
|     0 |        1 |         10 |             10 |
|     1 |        0 |         25 |             25 |
|     2 |        0 |         30 |             30 |
|     3 |        0 |         25 |             25 |
|     4 |       -1 |         22 |             22 |
|     5 |        0 |         20 |             22 |
|     6 |        0 |         21 |             22 |
|     7 |        1 |         16 |             16 |
|     8 |        0 |         11 |             11 |
|     9 |       -1 |         20 |             20 |
+-------+----------+------------+----------------+
position
指示何时采取某个位置<代码>1表示购买&
-1
表示出售

我首先在指数0处分配100美元,其中价格由
close
表示,即
10
&当价格为
22
时,我在指数4处卖出,因此我的投资组合增加了120%,这使我的投资额达到
100+120=220
。在指数
5
6
上,我没有持仓,因此我的投资组合变动为0%,我将维持220美元

在指数
7
时,我再次买入,但这次不是用100美元,而是用220美元以收盘价
16
买入,然后在
20
卖出,从而使我的投资组合增加了25%。现在我将拥有
220+55=275

我已经使用下面的代码生成了列
change
,该列告诉关于指数0的价格变化&
pct\u change
计算基准价格的百分比变化。我想根据列
位置动态更改下面代码第3行中的基价,即
df.close.iloc[0]
。在索引
7
中,我想将
df.close.iloc[0]
df.close.iloc[7]
一起更改第3行中的
df.close.iloc[0]
&我想
alloc
更改为
220
,因为现在我将投资220美元,因为我将获得一个新职位

下面代码的第2行也计算了指数0的收盘价差,这在指数
6
之前是可以的,但从指数
7
开始,我想计算指数7的收盘价差

alloc = 100 # allocation amount
df['change_cumsum'] = df.close_position.diff().cumsum()
df['pct_change_cumsum'] = alloc + ((df.change_cumsum / df.close.iloc[0]) * alloc)
电流输出:

+-------+----------+-------+----------------+---------------+-------------------+
| index | position | close | close_position | change        | pct_change        |
+-------+----------+-------+----------------+---------------+-------------------+
|     0 |        1 |    10 |             10 | NaN           | NaN               |
|     1 |        0 |    25 |             25 | 15            | 250               |
|     2 |        0 |    30 |             30 | 20            | 300               |
|     3 |        0 |    25 |             25 | 15            | 250               |
|     4 |       -1 |    22 |             22 | 12            | 220               |
|     5 |        0 |    20 |             22 | 12            | 220               |
|     6 |        0 |    21 |             22 | 12            | 220               |
|     7 |        1 |    16 |             16 | 6             | 160               |
|     8 |        0 |    11 |             11 | 1             | 110               |
|     9 |        0 |    20 |             20 | 10            | 200               |
+-------+----------+-------+----------------+---------------+-------------------+
期望输出:

+-------+----------+-------+----------------+---------------+-------------------+
| index | position | close | close_position | change.       | pct_change        |
+-------+----------+-------+----------------+---------------+-------------------+
|     0 |        1 |    10 |             10 |             0 |                 0 |
|     1 |        0 |    25 |             25 |            15 |               250 |
|     2 |        0 |    30 |             30 |            20 |               300 |
|     3 |        0 |    25 |             25 |            15 |               250 |
|     4 |       -1 |    22 |             22 |            12 |               220 |
|     5 |        0 |    20 |             22 |            12 |               220 |
|     6 |        0 |    21 |             22 |            12 |               220 |
|     7 |        1 |    16 |             16 |             0 |                220|
|     8 |        0 |    11 |             11 |            -5 |            151.25 |
|     9 |        0 |    20 |             20 |             4 |               275 |
+-------+----------+-------+----------------+---------------+-------------------+

以下是我对您问题的解决方案:

<>首先,我添加一个<代码> NETX位置< /代码>列来考虑您的累积位置。考虑到该头寸只在第二天有效(在市场关闭时买入),我将其移位1

df['net_position']=df.position.cumsum().shift().fillna(0)
然后,计算投资价值的方法是计算每次收盘之间的百分比变化。通过将此乘以累积位置,只考虑位置不为空时的更改。最后,将一个添加到此更改百分比以获得相对更改,并执行累积产品以获得投资的更改百分比

df['change']=(df.close.pct_change()*df.net_position+1.cumprod()*alloc
位置关闭位置净位置变化
0   1           10      10              0.0 
1   0           25      25              1.0             250
2   0           30      30              1.0             300
3   0           25      25              1.0             250
4   -1          22      22              1.0             220
5   0           20      22              0.0             220
6   0           21      22              0.0             220
7   1           16      16              0.0             220
8   0           11      11              1.0             151.25
9   0           20      20              1.0             275

我想我注意到您期望的输出中有一个不一致的地方:您的列
pct\u change
是您在alloc位置的百分比变化。我想知道你对指数7有什么想法:你的仓位变动率为0%,但在指数8,我希望看到的是-31,而不是151.25。这篇专栏实际上是关于什么的?如果我在指数7上分配220美元,我将采取新的立场,在指数7上,我的投资组合的百分比变化将为0%,因此指数7上的价值应该是220美元(这是我编辑的错误)。但如果你从220美元减少了-31%,那么你应该在指数8上得到151.25美元,这是正确的。Ok现在有意义了!如果我有办法在不需要
更改的情况下找到
pct\U更改
,您是否仍然可以接受?是的,可以接受。此解决方案不考虑分配金额,仅在初始分配为100美元时有效。我在问题中使用了分配作为变量&我希望它在解决方案中被视为一个变量。如果我错了,请告诉我,但您只需要将
df['change%']
乘以alloc即可。cumprod假设您将上次销售所得的资金全部再投资。无论原始的
alloc
有多大,它都可以工作(例如,尝试使用200)。我编辑了我的答案。是的,这样做的任务是<代码> df['嫦娥%] 乘以分配。它已经在我回答的结尾提到了,但没关系,我做了编辑,直接考虑<代码> OLC/<代码>。