-1

我想运行两个 for 循环,在其中我计算基于移动平均交叉的假设交易策略的年化回报。这很简单:只要“较快”的 MA 越过“较慢”的 MA,就做多。否则转移到现金。

我的数据如下所示:

在此处输入图像描述

我的代码:

rets = {}
ann_rets = {}

#Nested Loop to calculate returns
for short in range(20, 200):
    for long in range(short + 1, 200):
        
        #Calculate cumulative return
        rets[short,long] = (aapl[short,long][-1] - aapl[short,long][1]) / aapl[short,long][1]
        
        #calculate annualized return
        ann_rets[short,long] = (( 1 + rets[short,long]) ** (12 / D))-1 

我得到的错误信息如下:

TypeError: list indices must be integers or slices, not tuple

编辑:使用字典工作正常。下面的屏幕截图显示了我目前卡在哪里。我想要最后三列: (SMA_1,SMA_2,Ann_rets) SMA_1:第一个移动平均线,例如 20 SMA_2:第二个移动平均线,例如 50 Ann_rets:在上面的循环中计算的年化回报 在此处输入图像描述

4

3 回答 3

1

您正在尝试使用此处的元组访问列表的索引:rets[short,long].

尝试使用字典。所以改变

rets = []
ann_rets = []

rets = {}
ann_rets = {}
于 2021-01-19T12:40:45.017 回答
1

双索引 likerets[short, long]将适用于 NumPy 数组和 Pandas 数据帧(可能是您的aapl变量),但不适用于常规 Python 列表。改为使用rets[short][long]。(这也意味着您需要更改rests代码顶部的初始化。)

为了简要解释实际的错误消息:元组或多或少由分隔逗号定义,即 Python 看到short,long并将其转换为 tuple (short, long),然后在列表索引中使用。当然,这会失败,并抛出此错误消息。

于 2021-01-19T12:41:28.393 回答
1

我试着理解你的问题。希望这可以帮助。我简化了您的输出ann_rets以说明重新格式化为预期的输出格式。氪

rets = {}
ann_rets = {}

#Nested Loop to calculate returns
for short in range(20, 200):
    for long in range(short + 1, 200):
        
        #Calculate cumulative return
        rets[short,long] = (aapl[short,long][-1] - aapl[short,long][1]) / aapl[short,long][1]
        
        #calculate annualized return
        ann_rets[short,long] = (( 1 + rets[short,long]) ** (12 / D))-1 
        

# Reformat
Example data:
ann_rets = {(1,2): 0.1, (3,4):0.2, (5,6):0.3}
df1 = pd.DataFrame(ann_rets.values())
df2 = pd.DataFrame(list(ann_rets.keys()))
df = pd.concat([df2, df1], axis=1)
df.columns = ['SMA_1','SMA_2','Ann_rets']
print(df)

产生:

   SMA_1  SMA_2  Ann_rets
0      1      2       0.1
1      3      4       0.2
2      5      6       0.3
于 2021-01-19T12:56:48.707 回答