因此,我决定最近学习python以便对产品组合进行回测,而我偶然发现了时间优化问题。
我编写的函数可以正常工作,但是要花很多时间才能计算出来。我读到这一定是由于不同的循环造成的。
因此,我想知道是否有一种优化此代码的方法。
在多个条件下的第一个条件下,我尝试使用np.where,但它给了我一个错误
data['cash'] = np.where((data['Position'] == 1) & (data['signal']==1), (data['positions']=data['cash'].iloc[row-1]/data['Close'].iloc[row]*0.9)&(data['cash'].iloc[row] =data['positions'].iloc[row] *data['Close'].iloc[row]), 0)
必要进口
import pandas as pd
import numpy as np
这是一种简单的平均分频策略
def smasig (data, fast_days,slow_days, threshold):
data['FMA'] = data['Close'].rolling(center=False,window=fast_days, min_periods=fast_days).mean()
data['SMA'] = data['Close'].rolling(center=False,window=slow_days, min_periods=slow_days).mean()
data['FMA-SMA'] = data['FMA'] - data['SMA']
Threshold = threshold
data['Position']=0
data['Position'] = np.where(data['FMA']>data['SMA'],1.0,0.0)
data['signal']=data['Position'].diff()
此功能正常运行,但我想对其进行优化
def backtest(data, init):
data['cash'] =0.0
data['positions']=0
initial = init
for row in range(len(data)):
if row == 1:
data['cash']= initial
row+=1
if (data['Position'].iloc[row] == 1) and (data['signal'].iloc[row]==1):
data['positions'].iloc[row]=data['cash'].iloc[row-1]/data['Close'].iloc[row]
data['cash'].iloc[row] =data['positions'].iloc[row] *data['Close'].iloc[row]
elif (data['Position'].iloc[row] == 1) and (data['signal'].iloc[row]==0):
data['positions'].iloc[row] = data['positions'].iloc[row-1]
data['cash'].iloc[row] =data['positions'].iloc[row] *data['Close'].iloc[row]
elif (data['Position'].iloc[row] == 0) and (data['signal'].iloc[row]==-1):
data['positions'].iloc[row] = 0
data['cash'].iloc[row] = data['cash'].iloc[row-1]
elif (data['Position'].iloc[row] == 0) and (data['signal'].iloc[row]==0):
data['positions'].iloc[row] = 0
data['cash'].iloc[row] = data['cash'].iloc[row-1]
(data['Close'] / data['Close'].iloc[1]).plot()
(data['cash']/initial).plot()
这是执行力
GSPC =pd.read_csv(r"C:\Users\****\^GSPC.csv",index_col = "Date",
parse_dates=True, na_values=['nan'])
smasig(GSPC, 7,28,0)
backtest(GSPC,1000)
print(GSPC[['Position','signal', 'cash']].tail(10))
我希望得到的结果是相同的结果,但是速度更快。有办法吗?
提前感谢您的时间,如果不清楚,请告诉我。
您可以在Yahoo下载每日价格数据,选择开始日期为2014年5月15日,结束日期为2019年5月15日
更新: 这是我想要的代码类型,但是此代码没有预期的结果
Expected results Results obtained
def backtest (data, init):
data['cash'] =init
data['positions']=0
initial = init
data['cash'] = np.where(
(data['Position'] == 1) & (data['signal']==1),(
data['positions']==data['cash'].shift(1)/data['Close'])&(
data['cash'] ==data['positions'] *data['Close']),
np.where((data['Position'] == 1) & (data['signal']==0),
(data['positions'] == data['positions'].shift(1))&
(data['cash'] ==data['positions'] *data['Close']),
(data['positions'] == 0)& (data['cash'] == data['cash'].shift(1))))
(data['Close'] / data['Close'].iloc[1]).plot()
(data['cash']/initial).plot()