#coding:utf-8importnumpyasnpimportpandasaspdimportmatplotlib.pyplotaspltfrom__future__importdivision#获取数据函数defget_stock_data(stock_code,index_code,start_date,end_date)::paramstock_code:股票代码,例如‘sz000002’:paramindex_code:指数代码,例如‘sh000001’:paramstart_date:回测开始日期,例如‘1991-1-30':paramend_date:回测结束日期,例如‘2015-12-31’:return:函数返回其他函数的各参数序列#此处为存放csv文件的本地路径,请自行改正地址.注意windows和mac系统,斜杠的方向不一样stock_data=pd.read_csv(r'G:\财通实习\历史日线数据_样本%2820132014年数据%292\all_trading_data\stockdata\sh600000.csv',parse_dates=['date'])benchmark=pd.read_csv(r'G:\财通实习\历史日线数据_样本%2820132014年数据%292\all_trading_data\indexdata\sh000001.csv',parse_dates=['date'])date=pd.date_range(2016-01-01,2016-03-15)#生成日期序列#选取在日期范围内的股票数据序列并按日期排序stock_data=stock_data.ix[stock_data['date'].isin(date),['date','change','adjust_price']]stock_data=stock_data.ix[stock_data['date'].isin(date),['date','change','adjust_price']]#选取在日期范围内的指数数据序列并按日期排序date_list=list(stock_data['date'])benchmark=benchmark.ix[benchmark['date'].isin(date_list),['date','change','close']]benchmark.sort_values(by='date',inplace=True)benchmark.set_index('date',inplace=True)#将回测要用到的各个数据序列转成list格式date_line=list(benchmark.index.strftime('%Y-%m-%d'))#日期序列capital_line=list(stock_data['adjust_price'])#账户价值序列return_line=list(stock_data['change'])#收益率序列indexreturn_line=list(benchmark['change'])#指数的变化率序列index_line=list(benchmark['close'])#指数序列returndate_line,capital_line,return_line,index_line,indexreturn_line#计算年化收益率函数defannual_return(date_line,capital_line)::paramdate_line:日期序列:paramcapital_line:账户价值序列:return:输出在回测期间的年化收益率#将数据序列合并成dataframe并按日期排序df=pd.DataFrame({'date':date_line,'capital':capital_line})df.sort_values(by='date',inplace=True)df.reset_index(drop=True,inplace=True)rng=pd.period_range(df['date'].iloc[0],df['date'].iloc[-1],freq='D')#计算年化收益率annual=pow(df.ix[len(df.index)-1,'capital']/df.ix[0,'capital'],250/len(rng))-1print'年化收益率为:%f'%annual#计算最大回撤函数defmax_drawdown(date_line,capital_line)::paramdate_line:日期序列:paramcapital_line:账户价值序列:return:输出最大回撤及开始日期和结束日期#将数据序列合并为一个dataframe并按日期排序df=pd.DataFrame({'date':date_line,'capital':capital_line})df.sort_values(by='date',inplace=True)df.reset_index(drop=True,inplace=True)df['max2here']=pd.expanding_max(df['capital'])#计算当日之前的账户最大价值df['dd2here']=df['capital']/df['max2here']-1#计算当日的回撤#计算最大回撤和结束时间temp=df.sort_values(by='dd2here').iloc[0][['date','dd2here']]max_dd=temp['dd2here']end_date=temp['date']#计算开始时间df=df[df['date']=end_date]start_date=df.sort_values(by='capital',ascending=False).iloc[0]['date']print'最大回撤为:%f,开始日期:%s,结束日期:%s'%(max_dd,start_date,end_date)#计算平均涨幅defaverage_change(date_line,return_line)::paramdate_line:日期序列:paramreturn_line:账户日收益率序列:return:输出平均涨幅df=pd.DataFrame({'date':date_line,'rtn':return_line})ave=df['rtn'].mean()print'平均涨幅为:%f'%ave#计算上涨概率defprob_up(date_line,return_line)::paramdate_line:日期序列:paramreturn_line:账户日收益率序列:return:输出上涨概率df=pd.DataFrame({'date':date_line,'rtn':return_line})df.ix[df['rtn']0,'rtn']=1#收益率大于0的记为1df.ix[df['rtn']=0,'rtn']=0#收益率小于等于0的记为0#统计1和0各出现的次数count=df['rtn'].value_counts()p_up=count.loc[1]/len(df.index)print'上涨概率为:%f'%p_up#计算最大连续上涨天数和最大连续下跌天数defmax_successive_up(date_line,return_line)::paramdate_line:日期序列:paramreturn_line:账户日收益率序列:return:输出最大连续上涨天数和最大连续下跌天数df=pd.DataFrame({'date':date_line,'rtn':return_line})#新建一个全为空值的series,并作为dataframe新的一列s=pd.Series(np.nan,index=df.index)s.name='up'df=pd.concat([df,s],axis=1)#当收益率大于0时,up取1,小于0时,up取0,等于0时采用前向差值df.ix[df['rtn']0,'up']=1df.ix[df['rtn']0,'up']=0df['up'].fillna(method='ffill',inplace=True)#根据up这一列计算到某天为止连续上涨下跌的天数rtn_list=list(df['up'])successive_up_list=[]num=1foriinrange(len(rtn_list)):ifi==0:successive_up_list.append(num)else:if(rtn_list[i]==rtn_list[i-1]==1)or(rtn_list[i]==rtn_list[i-1]==0):num+=1else:num=1successive_up_list.append(num)#将计算结果赋给新的一列'successive_up'df['successive_up']=successive_up_list#分别在上涨和下跌的两个dataframe里按照'successive_up'的值排序并取最大值max_successive_up=df[df['up']==1].sort_values(by='successive_up',ascending=False)['successive_up'].iloc[0]max_successive_down=df[df['up']==0].sort_values(by='successive_up',ascending=False)['successive_up'].iloc[0]print'最大连续上涨天数为:%d最大连续下跌天数为:%d'%(max_successive_up,max_successive_down)#计算最大单周期涨幅和最大单周期跌幅defmax_period_return(date_line,return_line)::paramdate_line:日期序列:paramreturn_line:账户日收益率序列:return:输出最大单周期涨幅和最大单周期跌幅df=pd.DataFrame({'date':date_line,'rtn':return_line})#分别计算日收益率的最大值和最小值max_return=df['rtn'].max()min_return=df['rtn'].min()print'最大单周期涨幅为:%f最大单周期跌幅为:%f'%(max_return,min_return)#计算收益波动率的函数defvolatility(date_line,return_line)::paramdate_line:日期序列:paramreturn_line:账户日收益率序列:return:输出回测期间的收益波动率frommathimportsqrtdf=pd.DataFrame({'date':date_line,'rtn':return_line})#计算波动率vol=df['rtn'].std()*sqrt(250)print'收益波动率为:%f'%vol#计算贝塔的函数defbeta(date_line,return_line,indexreturn_line)::paramdate_line:日期序列:paramreturn_line:账户日收益率序列:paramindexreturn_line:指数的收益率序列:return:输出beta值df=pd.DataFrame({'date':date_line,'rtn':return_line,'benchmark_rtn':indexreturn_line})#账户收益和基准收益的协方差除以基准收益的方差b=df['rtn'].cov(df['benchmark_rtn'])/df['b