我自己做网站,线上注册公司流程和费用,wordpress微信公众号插件,网站建设课程小结本人之前写过若干“给程序员加财商”的系列文#xff0c;目的是通过股票案例讲述Python知识点#xff0c;让大家在学习Python的同时还能掌握相关的股票知识#xff0c;所谓一举两得。 在之前的系列文里#xff0c;大家能看到K线#xff0c;均线#xff0c;成交量的案例目的是通过股票案例讲述Python知识点让大家在学习Python的同时还能掌握相关的股票知识所谓一举两得。 在之前的系列文里大家能看到K线均线成交量的案例在本文里大家能看到通过RSI案例讲述Python邮件编程的知识点在后继系列文里大家还能看到MACD,BIAS,KDJ等指标相关案例。 1 RSI指标的原理和算法描述 相对强弱指标RSI是通过比较某个时段内单股价格的涨跌幅度来判断多空双方的强弱程度以此来预测未来走势。从数值上看它体现出某股的买卖力量所以投资者能据此预测未来价格的走势在实践中通常与移动平均线配合使用以提高分析的准确性。 RSI指标的计算公式如下所示。 第一步RS相对强度N日内收盘价涨数和的均值÷N日内收盘价跌数和的均值 第二步RSI相对强弱指标100100÷1RS 请注意这里“均值“的计算方法可以是简单移动平均SMA也可以是加权移动平均WMA指数移动平均EMA。本书采用的是比较简单的简单移动平均算法有些软件采用的是后两种平均算法。采用不同的平均算法会导致RSI的值不同但趋势不会改变对交易的指导意义也不会变。 以6日RSI指标为例从当日算起向前推算6个交易日获取到包括本日在内的7个收盘价用每一日的收盘价减去上一交易日的收盘价以此方式得到6个数值这些数值中有正有负。随后再按如下四个步骤计算RSI指标。 第一步up6个数字中正数之和的平均值。 第二步down先取6个数字中负数之和的绝对值再对绝对值取平均值。 第三步RSup除以downRS表示相对强度 第四步RSI相对强弱指标100100÷1RS 如果再对第四步得出的结果进行数学变换能进一步约去RS因素得到如下的结论RSI100x(up) ÷(updown)也就是说RSI等于100乘以up除以(up和down的和)。 从本质上来看RSI反映了某阶段内比如6个交易日内由价格上涨引发的波动占总波动的百分比率百分比越大说明这个时间段内股票越强势反之如果百分比越小则说明股票弱势程度强。 从上述公式中我们能看到RSI的值介于0到100之间目前比较常见的基准周期为6日\12日和24日。把每个交易日的RSI值在坐标图上的点连成曲线即能绘制成RSI指标线也就是说目前沪深股市中RSI指标线是由三根曲线构成如下图所示。 2 把用Matplotlib绘制的RSI指标图存为图片 在如下的DrawRSI.py案例中我们将根据上述算法绘制600584长电科技从2018年9月到2019年5月间的的6日、12日和24日的RSI指标。 本例的数据来自csv文件而该文件的数据来自网络股票接口相关内容大家可以阅读之前博文。在本案例中还会把由matplotlib生成的图形存为png格式以方便之后用邮件的形式发送。 1 #!/usr/bin/env python
2 #codingutf-8
3 import pandas as pd
4 import matplotlib.pyplot as plt
5 #计算RSI的方法入参periodList传入周期列表
6 def calRSI(df,periodList):
7 #计算和上一个交易日收盘价的差值
8 df[diff] df[Close]-df[Close].shift(1)
9 df[diff].fillna(0, inplace True)
10 df[up] df[diff]
11 #过滤掉小于0的值
12 df[up][df[up]] 0
13 df[down] df[diff]
14 #过滤掉大于0的值
15 df[down][df[down]] 0
16 #通过for循环依次计算periodList中不同周期的RSI等值
17 for period in periodList:
18 df[upAvgstr(period)] df[up].rolling(period).sum()/period
19 df[upAvgstr(period)].fillna(0, inplace True)
20 df[downAvgstr(period)] abs(df[down].rolling(period).sum()/period)
21 df[downAvgstr(period)].fillna(0, inplace True)
22 df[RSIstr(period)] 100 - 100/((df[upAvgstr(period)]/df[downAvgstr(period)]1))
23 return df在第5行里我们定义了用于计算RSI值的calRSI方法该方法第一个参数是包含日期收盘价等信息的dataframe类型的df对象第二个参数是周期列表。 在第8行里我们把本交易日和上个交易日收盘价的差价存入了diff列这里是用shift(1)来获取df里上一行即上个交易日的收盘价。由于第一行的diff值是NaN所以需要用第9行的fillna方法把NaN值更新成0。 在第11行里在df对象里创建了up列该列的值暂时和diff值相同有正有负但马上就通过第12行的df[up][df[up]0] 0代码把up列中的负值设置成0这样一来up列里就只包含了“N日内收盘价的涨数”。在第13行和第15行里用同样的方法在df对象中创建了down列并在其中存入了“N日内收盘价的跌数”。 随后是通过第17行的for循环遍历存储在periodList中的周期对象其实通过下面第26行的代码我们能看到计算RSI的周期分别是6天、12天和24天。针对每个周期先是在第18行算出了这个周期内收盘价涨数和的均值并把这个均值存入df对象中的upAvgstr(period)列中比如当前周期是6那么该涨数的均值是存入df[‘upAvg6‘]列。在第20行则算出该周期内的收盘价跌数的均值并存入downAvgstr(period)列中。最后在第22行算出本周期内的RSI值并放入df对象中的RSIstr(period)里。 24 filenameD:\\stockData\ch10\\6005842018-09-012019-05-31.csv
25 df pd.read_csv(filename,encodinggbk)
26 list [6,12,24] #周期列表
27 #调用方法计算RSI
28 stockDataFrame calRSI(df,list)
29 #print(stockDataFrame)
30 #开始绘图
31 plt.figure()
32 stockDataFrame[RSI6].plot(colorblue,labelRSI6)
33 stockDataFrame[RSI12].plot(colorgreen,labelRSI12)
34 stockDataFrame[RSI24].plot(colorpurple,labelRSI24) 35 plt.legend(locbest) #绘制图例 36 #设置x轴坐标标签和旋转角度 37 major_indexstockDataFrame.index[stockDataFrame.index0] 38 major_xticsstockDataFrame[Date][stockDataFrame.index0] 39 plt.xticks(major_index,major_xtics) 40 plt.setp(plt.gca().get_xticklabels(), rotation30) 41 #带网格线且设置了网格样式 42 plt.grid(linestyle-.) 43 plt.title(RSI效果图) 44 plt.rcParams[font.sans-serif][SimHei] 45 plt.savefig(D:\\stockData\ch10\\6005842018-09-012019-05-31.png) 46 plt.show() 在第25行里我们从指定csv文件里得到了包含日期收盘价等信息的数据并在第26行指定了三个计算周期。在第28行里我们调用了calRSI方法计算了三个周期的RSI值并存入stockDataFrame对象当前第29行的输出语句是注释掉的在打开后大家能看到计算后的结果值其中包含upAvg6、downAvg6和RSI6等列。 在得到RSI数据后从第31行开始绘图其中比较重要的步骤是通过第32行到第34行的代码用plot方法绘制三根曲线随后通过第35行的legend方法设置图例通过第37行和第38行的代码设置x轴刻度的文字以及旋转效果通过第42行的代码设置网格样式通过第43的代码设置标题。 在第46行通过show方法绘图前我们通过第45行的代码用savefig方法把图形保存到了指定目录请注意这句话需要放在show方法前否则保存的图片就会是空的。 运行上述代码能看到如下图所示的RSI效果图。需要说明的是由于本例在计算收盘价涨数和均值和收盘价跌数和均值时用的是简单移动平均算法所以绘制出来的图形可能和一些软件里的不一致但趋势相同。而且在指定目录里能看到png图片。 3 整合K线后用邮件发送 在DrawKwithRSI.py代码里我们将完成如下三个工作第一计算6日、12日和24日的RSI值。第二绘制K线加均线加RSI指标图并把结果保存为png格式图片。第三发送邮件并把png图片以富文本的格式展示在邮件正文中。 1 #!/usr/bin/env python
2 #codingutf-8
3 import pandas as pd
4 import matplotlib.pyplot as plt
5 from mpl_finance import candlestick2_ochl
6 from matplotlib.ticker import MultipleLocator
7 import smtplib
8 from email.mime.text import MIMEText
9 from email.mime.image import MIMEImage
10 from email.mime.multipart import MIMEMultipart
11 #计算RSI的方法入参periodList传入周期列表
12 def calRSI(df,periodList):
13 和DrawRSI.py案例中的一致 从第3行到第10行我们引入了相关的库文件第12行定义的calRSI方法和之前案例中的完全一致所以就不再给出代码。 14 filenameD:\\stockData\ch10\\6005842018-09-012019-05-31.csv
15 df pd.read_csv(filename,encodinggbk)
16 list [6,12,24] #周期列表
17 #调用方法计算RSI
18 stockDataFrame calRSI(df,list)
19 figure plt.figure()
20 #创建子图
21 (axPrice, axRSI) figure.subplots(2, sharexTrue)
22 #调用方法在第axPrice子图里绘制K线图
23 candlestick2_ochl(ax axPrice, opensdf[Open].values, closesdf[Close].values, highsdf[High].values, lowsdf[Low].values,width0.75, colorupred, colordowngreen)
24 axPrice.set_title(K线图和均线图)#设置子图标题
25 stockDataFrame[Close].rolling(window3).mean().plot(axaxPrice,colorred,label3天均线)
26 stockDataFrame[Close].rolling(window5).mean().plot(axaxPrice,colorblue,label5天均线)
27 stockDataFrame[Close].rolling(window10).mean().plot(axaxPrice,colorgreen,label10天均线)
28 axPrice.legend(locbest) #绘制图例
29 axPrice.set_ylabel(价格单位元)
30 axPrice.grid(linestyle-.) #带网格线
31 #在axRSI子图里绘制RSI图形
32 stockDataFrame[RSI6].plot(axaxRSI,colorblue,labelRSI6)
33 stockDataFrame[RSI12].plot(axaxRSI,colorgreen,labelRSI12)
34 stockDataFrame[RSI24].plot(axaxRSI,colorpurple,labelRSI24)
35 plt.legend(locbest) #绘制图例
36 plt.rcParams[font.sans-serif][SimHei]
37 axRSI.set_title(RSI图)#设置子图的标题
38 axRSI.grid(linestyle-.) #带网格线
39 #设置x轴坐标标签和旋转角度
40 major_indexstockDataFrame.index[stockDataFrame.index%70]
41 major_xticsstockDataFrame[Date][stockDataFrame.index%70]
42 plt.xticks(major_index,major_xtics)
43 plt.setp(plt.gca().get_xticklabels(), rotation30)
44 plt.savefig(D:\\stockData\ch10\\600584RSI.png)在第18行里我们通过调用calRSI方法得到了三个周期的RSI数据。在第21行里设置了axPrice和axRSI这两个子图共享x轴标签在第23行里绘制了K线图在第25行到第27行里绘制了3日、5日和10日的均线在第32行到第34行里绘制了6日、12日和24日的三根RSI指标图。在第44行里通过savefig方法把包含K线、均线和RSI指标线的图形存在指定目录中。 45 #发送邮件
46 def sendMail(username,pwd,from_addr,to_addr,msg):
47 和之前sendMailWithPicAttachment.py案例中的一致
48 def buildMail(HTMLContent,subject,showFrom,showTo,attachfolder,attachFileName):
49 message MIMEMultipart()
50 body MIMEText(HTMLContent, html, utf-8)
51 message.attach(body)
52 message[Subject] subject
53 message[From] showFrom
54 message[To] showTo
55 imageFile MIMEImage(open(attachfolderattachFileName, rb).read())
56 imageFile.add_header(Content-ID, attachFileName)
57 imageFile[Content-Disposition] attachment;filenameattachFileName
58 message.attach(imageFile)
59 return message第46行定义的sendMail方法和之前案例中的完全一致所以就不给出详细的代码。本案例与之前不同的是在第48行里专门定义了buildMail方法用来组装邮件对象邮件的诸多要素由该方法的参数所定义。 具体而言在第49行里定义邮件类型是MIMEMultipart也就是说带附件的邮件在第50行和第51行里根据参数HTMLContent构建了邮件的正文在第52行到第54行里设置了邮件的相关属性值从第55行到第57行根据入参构建了MIMEImage类型的图片类附件在第58行里通过attach方法把附件并入邮件正文。 60 subjectRSI效果图
61 attachfolderD:\\stockData\\ch10\\
62 attachFileName600584RSI.png
63 HTMLContent htmlhead/headbody\
64 img srccid:attachFileName/\
65 /body/html
66 message buildMail(HTMLContent,subject,hsm_computer163.com,hsm_computer163.com,attachfolder,attachFileName)
67 sendMail(hsm_computer,xxx,hsm_computer163.com,hsm_computer163.com,message.as_string())
68 #最后再绘制
69 plt.show()在第60行到第66行我们设置了邮件的相关属性值并在第66行里通过调用buildMail方法创建了邮件对象message在第第67行里通过调用sendMail方法发送邮件最后在第69行通过show方法绘制了图形。请大家注意本案例中的三个细节。 第一 第64行cid的值需要和第56行的Content-ID值一致否则图片只能以附件的形式发送无法在邮件正文里以富文本的格式展示。 第二 我们是先构建和发送邮件再通过第69行的代码绘制图形如果次序颠倒先绘制图形后发送邮件的话show方法被调用后程序会阻塞在这个位置代码无法继续执行。要等到手动关闭掉由show方法弹出的窗口后才会触发sendMail方法发送邮件。 第三 在本案例的第48行我们专门封装了用于构建邮件对象的buildMail方法在其中通过参数动态地构建邮件这样如果要发送其它邮件则可以调用该方法从而能提升代码的重用性。 运行上述代码我们能在弹出的窗口里看到K线、均线和RSI指标图整合后的效果图而且能在邮件的正文里看到相同的图。 4 RSI指标对买卖点的指导意义 一般来说我们把6日、12日和24日的RSI指标称为为短期、中期和长期指标。和KDJ指标一样RSI指标也有超买和超卖区。 具体而言当RSI值在50到70间波动时表示当前属于强势状态如继续上升超过80时,则到超买区,极可能在短期内转升为跌。反之RSI值在20到50之间时说明当前市场处于相对弱势如下降到20以下,则进入超卖区股价可能出现反弹。 在讲述RSI交易策略前我们先来讲述下在实际操作中总结出来的RSI指标的缺陷。 第一周期较短比如6日的RSI指标比较灵敏但快速震荡的次数较多可靠性相对差些而周期较长比如24日的RSI指标可靠性强但灵敏度不够经常会“滞后”的情况。 第二当数值在40到60间波动时往往参考价值不大具体而言当数值向上突破50临界点时表示股价已转强反之向下跌破50时则表示转弱不过在实践过程中经常会出现RSI跌破50后股价却不下跌而突破50后股价不涨。 综合RSI算法、相关理论以及缺陷我们来讲述下实际操作中常用的基于该指标的卖策略。 第一RSI短期指标6日在20以下超卖区与中长期RSI12日或24日发生黄金交叉即6日线上穿12日或24日线则说明即将发生反弹行情如果其它技术或政策等方面没太大问题可以适当买进。 第二反之RSI短期指标6日在80以上超买区与中长期RSI12日或24日发生死亡交叉即6日线下穿12日或24日线则说明可能会出现高位反转的情况如果没有其它利好消息可以考虑卖出。 5 计算卖点以邮件的形式发送 根据上文描述这里采用的基于RSI的买点策略是RSI6日线在20以下与中长期RSI12日或24日发生黄金交叉。在如下的calRSIBuyPoints.py案例中我们据此策略计算600584长电科技从2018年9月到2019年5月间的卖点而且通过邮件发送买点日期。 1 #!/usr/bin/env python
2 #codingutf-8
3 import pandas as pd
4 import smtplib
5 from email.mime.text import MIMEText
6 from email.mime.image import MIMEImage
7 from email.mime.multipart import MIMEMultipart
8 #计算RSI的方法入参periodList传入周期列表
9 def calRSI(df,periodList):
10 和DrawRSI.py案例中的一致省略相关代码
11 filenameD:\\stockData\ch10\\6005842018-09-012019-05-31.csv
12 df pd.read_csv(filename,encodinggbk)
13 list [6,12,24] #周期列表
14 #调用方法计算RSI
15 stockDataFrame calRSI(df,list) 在上述代码的第15行里我们通过调用calRSI方法计算RSI指标值这部分和10.3.2部分的calRSIBuyPoints.py相关代码非常相似所以就不再重复说明。 16 cnt0
17 sellDate
18 while cntlen(stockDataFrame)-1:
19 if(cnt30):#前几天有误差从第30天算起
20 try:
21 #规则1这天RSI6高于80
22 if stockDataFrame.iloc[cnt][RSI6]80:
23 #规则2.1,当天RSI6下穿RSI12
24 if stockDataFrame.iloc[cnt][RSI6]stockDataFrame.iloc[cnt][RSI12] and stockDataFrame.iloc [cnt-1][RSI6]stockDataFrame.iloc[cnt-1][RSI12]:
25 sellDate sellDatestockDataFrame.iloc[cnt][Date] ,
26 #规则2.2,当天RSI6下穿RSI24
27 if stockDataFrame.iloc[cnt][RSI6]stockDataFrame.iloc[cnt][RSI24] and stockDataFrame.iloc[cnt-1] [RSI6]stockDataFrame.iloc[cnt-1][RSI24]:
28 if sellDate.index(stockDataFrame.iloc[cnt][Date]) -1:
29 sellDate sellDatestockDataFrame.iloc[cnt][Date] ,
30 except:
31 pass
32 cntcnt1
33 print(sellDate)在第18行到第32行的while循环里我们计算了基于RSI的卖点在第22行的语句里我们制定了第一个规则RSI6数值大于80在第23行和第27行我们在规则一的基础上制定了两个并行的规则通过上述代码我们会在sellDate对象里存放RSI6大于80并且RSI6下穿RSI12或RSI24的交易日这些交易日即为卖点。 34 def sendMail(username,pwd,from_addr,to_addr,msg):
35 和之前calRSIBuyPoints.py案例中的完全一致
36 def buildMail(HTMLContent,subject,showFrom,showTo,attachfolder,attachFileName):
37 和之前calRSIBuyPoints.py案例中的完全一致
38 subjectRSI卖点分析
39 attachfolderD:\\stockData\\ch10\\
40 attachFileName600584RSI.png
41 HTMLContent htmlhead/headbody\
42 卖点日期 sellDate \
43 img srccid:attachFileName/\
44 /body/html
45 message buildMail(HTMLContent,subject,hsm_computer163.com,hsm_computer163.com,attachfolder,attachFileName)
46 sendMail(hsm_computer,xxx,hsm_computer163.com,hsm_computer163.com,message.as_string()) 第34行和第36行的两个用于发送邮件和构建构建的方法和之前案例的完全一致所以就不再额外说明。 在第38行我们定义的邮件标题是“RSI卖点分析”在第41行定义的描述正文的HTMLContent对象里我们存放的也是“卖点日期”最终是通过第46行调用sendMail方法发送邮件。 运行上述代码我们能看到如下图所示的邮件其中包括了卖点日期和指标图。这里通过计算得出的卖点日期比较多经分析这些日期之后股价多有下跌情况。 6 总结和版权说明 本文是给程序员加财商系列之前的系列文如下 以预测股票涨跌案例入门基于SVM的机器学习 用python的matplotlib和numpy库绘制股票K线均线和成交量的整合效果含量化验证交易策略代码 用python的matplotlib和numpy库绘制股票K线均线的整合效果含从网络接口爬取数据和验证交易策略代码 本文力争做到详细比如代码按行编号并针对行号详细解释且图文并茂所以如果大家感觉可以请尽量帮忙推荐一下。 本文的内容即将出书在出版的书里是用股票案例和大家讲述Python入门时的知识点敬请期待 有不少网友转载和想要转载我的博文本人感到十分荣幸这也是本人不断写博文的动力。关于本文的版权有如下统一的说明抱歉就不逐一回复了。 1 本文可转载无需告知转载时请用链接的方式给出原文出处别简单地通过文本方式给出同时写明原作者是hsm_computer。 2 在转载时请原文转载 谢绝洗稿。否则本人保留追究法律责任的权利。 转载于:https://www.cnblogs.com/JavaArchitect/p/11463091.html