当前位置:   article > 正文

MQL5学习之简单移动平均线MA的编写

MQL5学习之简单移动平均线MA的编写

昨天还是有点高估自己了,MACD相对较难一点,改学MA的编写,首先明确MA的计算,假如有4个值,p=[1,2, 3, 4], period=3,

则v[0]=p[0], v[1]=p[1],v[2]=(p[0]+p[1]+p[2])/3=2,

v[3]=(v[2]*3+p[3]-p[0])/3,

然后将v[3]的计算公式化简单就得到v[3]=v[2] + (p[3]-p[0])/3,把period,初始值i代进来,注意i从period开始:

v[i]=v[i-1] + (p[i]-p[i-period])/period

一句话解释即为第i个平均值的计算为i-1的位置的平均值加上一个计算值,这个计算值由第i位置的价格减去步长前的价格再除于步长period得到。

然后即可以来观察一下移动平均线的代码了:

  1. //+------------------------------------------------------------------+
  2. //| Custom Moving Average.mq5 |
  3. //| Copyright 2000-2024, MetaQuotes Ltd. |
  4. //| https://www.mql5.com |
  5. //+------------------------------------------------------------------+
  6. #property copyright "Copyright 2000-2024, MetaQuotes Ltd."
  7. #property link "https://www.mql5.com"
  8. //--- indicator settings
  9. #property indicator_chart_window
  10. #property indicator_buffers 2
  11. #property indicator_plots 2
  12. #property indicator_type1 DRAW_LINE
  13. #property indicator_color1 Red
  14. #property indicator_type2 DRAW_LINE
  15. #property indicator_color2 Silver
  16. //--- input parameters
  17. input int InpMAPeriod1=20;
  18. input int InpMAPeriod2=60;
  19. //--- indicator buffer
  20. double ExtLineBuffer1[];
  21. double ExtLineBuffer2[];
  22. //+------------------------------------------------------------------+
  23. //| Custom indicator initialization function |
  24. //+------------------------------------------------------------------+
  25. void OnInit()
  26. {
  27. //--- indicator buffers mapping
  28. SetIndexBuffer(0,ExtLineBuffer1,INDICATOR_DATA);
  29. SetIndexBuffer(1,ExtLineBuffer2,INDICATOR_DATA);
  30. //--- set accuracy
  31. IndicatorSetInteger(INDICATOR_DIGITS,_Digits+1);
  32. //--- set first bar from what index will be drawn
  33. PlotIndexSetInteger(0,PLOT_DRAW_BEGIN,InpMAPeriod1);
  34. PlotIndexSetInteger(1,PLOT_DRAW_BEGIN,InpMAPeriod2);
  35. //--- name for DataWindow
  36. string short_name ="SMA";
  37. IndicatorSetString(INDICATOR_SHORTNAME,short_name+"("+string(InpMAPeriod1)+")");
  38. IndicatorSetString(INDICATOR_SHORTNAME,short_name+"("+string(InpMAPeriod2)+")");
  39. //--- set drawing line empty value
  40. PlotIndexSetDouble(0,PLOT_EMPTY_VALUE,0.0);
  41. PlotIndexSetDouble(1,PLOT_EMPTY_VALUE,0.0);
  42. }
  43. //+------------------------------------------------------------------+
  44. //| Moving Average |
  45. //+------------------------------------------------------------------+
  46. int OnCalculate(const int rates_total,
  47. const int prev_calculated,
  48. const int begin,
  49. const double &price[])
  50. {
  51. if(rates_total<InpMAPeriod1-1+begin)
  52. return(0);
  53. //--- first calculation or number of bars was changed
  54. if(prev_calculated==0)
  55. {
  56. ArrayInitialize(ExtLineBuffer1,0);
  57. PlotIndexSetInteger(0,PLOT_DRAW_BEGIN,InpMAPeriod1-1+begin);
  58. PlotIndexSetInteger(1,PLOT_DRAW_BEGIN,InpMAPeriod2-1+begin);
  59. }
  60. //--- calculation
  61. CalculateSimpleMA(rates_total,prev_calculated,begin,price,ExtLineBuffer1, InpMAPeriod1);
  62. if(rates_total<InpMAPeriod2-1+begin)
  63. return(rates_total);
  64. else {
  65. CalculateSimpleMA(rates_total,prev_calculated,begin,price,ExtLineBuffer2, InpMAPeriod2);
  66. }
  67. //--- return value of prev_calculated for next call
  68. return(rates_total);
  69. }
  70. //+------------------------------------------------------------------+
  71. //| simple moving average |
  72. //+------------------------------------------------------------------+
  73. void CalculateSimpleMA(int rates_total,int prev_calculated,int begin,const double &price[], double &buffer[], int period)
  74. {
  75. int i,start;
  76. //--- first calculation or number of bars was changed
  77. if(prev_calculated==0)
  78. {
  79. start=period+begin;
  80. //--- set empty value for first start bars
  81. for(i=0; i<start-1; i++)
  82. buffer[i]=0.0;
  83. //--- calculate first visible value
  84. double first_value=0;
  85. for(i=begin; i<start; i++)
  86. first_value+=price[i];
  87. first_value/=period;
  88. buffer[start-1]=first_value;
  89. }
  90. else
  91. start=prev_calculated-1;
  92. //--- main loop
  93. for(i=start; i<rates_total && !IsStopped(); i++)
  94. buffer[i]=buffer[i-1]+(price[i]-price[i-period])/period;
  95. }

#property indicator_chart_window 这一行表达为主图显示,若想显示到副图,可改为#property indicator_separate_window

这一行表达为需要画两个变量:#property indicator_plots   2

这一行表达第二个画出来的变量用灰色:#property indicator_color2  Silver

程序:

input int            InpMAPeriod1=20;

input int            InpMAPeriod2=60;表示输入两个参数,一个为20,一个为60

初始化时需要针对变量0和变量1分别初始化:

   SetIndexBuffer(0,ExtLineBuffer1,INDICATOR_DATA);

   SetIndexBuffer(1,ExtLineBuffer2,INDICATOR_DATA);

代码CalculateSimpleMA中计算MA的核心代码为:

  1. for(i=start; i<rates_total && !IsStopped(); i++)
  2. buffer[i]=buffer[i-1]+(price[i]-price[i-period])/period;
  3. }

然后我们运行代码,会发现弹出参数,刚好是前面代码中定义的变量

运行出来的20均,60均的图形如下:

然后与通达信上的相比较,发现是一致的,说明计算无误

从目前实践的看起来,MQL5难度要显著高于通达信或是北极星什么的,唯一的好处是可以做极其复杂的计算,无限制的变量,类什么的,并可以做文件存储,网络传输,几乎能想到的一切,比如后面对接实盘时,官方对接实盘是收费的,如果你有程序化交易的程序接口,完全可在算法中直接http协议完成实盘交易。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/从前慢现在也慢/article/detail/198333
推荐阅读
相关标签
  

闽ICP备14008679号