欢迎您光临博庭社区!

 找回密码
 立即注册
查看: 12251|回复: 26

逐行和逐根 [复制链接]

Rank: 8Rank: 8

发表于 2012-9-18 12:06:13 |显示全部楼层
一。序列

要理解什么是逐行和逐根,首先要理解什么是“序列”。

在多数股软里,K线就是内置的序列。当然,一根K线实际上是由开高低收量额组成的。
所以也就有对应的close,open,high,low,vol,amount等五个内置序列。

序列是很特别的一类数据。它跟数组很相像:每个序列都由多个元素组成,可以通过下标访问。

序列跟数组的区别
数组在声明时已经定义好元素数量,之后不会改变;而序列在声明时并不指明元素数量。它的数量由K线数量决定,随着行情进行,K线不断增加,序列也相应的自动增加,并且是一一对应。

序列的下标:金语言中,序列下标0代表最近的一根K线所对应的序列数据;下标1代表前一根K线所对应的数据。

使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:06:58 |显示全部楼层
本帖最后由 ptLibert 于 2012-9-19 22:42 编辑

那么,在看过我们的指标实例之后,稍有传统语言编程经验的人都会立刻产生一个疑问。

那就是,实际上,在飞狐/tradestation等股软中,序列常常不通过下标直接使用。

例如这样的一句:
  • a1 : close - open;

复制代码

计算得到开盘价减去收盘价的值。并且是对于每根K线,a1都会得到一个对应的值。
也就是说,a1也是序列。

既然序列是数组,为什么可以不通过下标就直接使用?
根据传统编程经验,要得到数组中每一个元素的值,必须写一个循环,计算每个元素,产生新的结果。

例如这样:
  1. for i=1 to sizeof( close ) do begin
  2.     a1[i] := close[i] - open[i];
  3. end;
复制代码
为什么在指标中,可以不写这个循环呢?

答案是:指标引擎在背后默默的帮我们做了这份工作。

使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:08:38 |显示全部楼层
在股票类数据运算中,序列用得太多,太频繁,如果指标引擎不替用户做这份循环计算工作的话,那么用户编写程序的时候,将会非常的麻烦。




任何一个简单的操作,都要写上一大堆的循环。




有心人可以去观摩一个股软metaTrader,的指标。metaTrader是一个不替用户做序列循环计算的股软。
实现相同功能,它的源码要比其他的股软长的多。




举个简单例子,macd,在metaTrader里面要写这么多代码:
  1. //+------------------------------------------------------------------+
  2. //|                                                  Custom MACD.mq4 |
  3. //|                      Copyright ?2004, MetaQuotes Software Corp. |
  4. //|                                       http://www.metaquotes.net/ |
  5. //+------------------------------------------------------------------+
  6. #property  copyright "Copyright ?2004, MetaQuotes Software Corp."
  7. #property  link      "http://www.metaquotes.net/"
  8. //---- indicator settings
  9. #property  indicator_separate_window
  10. #property  indicator_buffers 3
  11. #property  indicator_color1  Silver
  12. #property  indicator_color2  Red
  13. #property  indicator_color3  Green
  14. #property  indicator_width1  2
  15. //---- indicator parameters
  16. extern int FastEMA=12;
  17. extern int SlowEMA=26;
  18. extern int SignalSMA=9;
  19. //---- indicator buffers
  20. double      DiffBuffer[];
  21. double     MacdBuffer[];
  22. double     SignalBuffer[];




  23. //+------------------------------------------------------------------+
  24. //| Custom indicator initialization function                         |
  25. //+------------------------------------------------------------------+
  26. int init()
  27.   {
  28. //---- drawing settings
  29.    //SetIndexStyle(0,DRAW_HISTOGRAM);
  30.    
  31.    SetIndexStyle( 0, DRAW_LINE );
  32.    SetIndexStyle(1,DRAW_LINE);
  33.    SetIndexStyle( 2, DRAW_HISTOGRAM);
  34.    
  35.    SetIndexDrawBegin(1,SignalSMA);
  36.    IndicatorDigits(Digits+1);
  37. //---- indicator buffers mapping
  38.    //SetIndexBuffer(0,MacdBuffer);
  39.    
  40.    SetIndexBuffer(0,DiffBuffer);
  41.    SetIndexBuffer(1,SignalBuffer);
  42.    SetIndexBuffer(2,MacdBuffer);
  43. //---- name for DataWindow and indicator subwindow label
  44.    IndicatorShortName("MACD("+FastEMA+","+SlowEMA+","+SignalSMA+")@@#");
  45.    //SetIndexLabel(0,"MACD");
  46.    //SetIndexLabel(1,"Signal");
  47.    SetIndexLabel(0,"Diff");
  48.    SetIndexLabel(1,"Dea");
  49.    SetIndexLabel(2,"MACD");
  50.    
  51. //---- initialization done
  52.    return(0);
  53.   }
  54. //+------------------------------------------------------------------+
  55. //| *****Moving Averages Convergence/Divergence  *****              |
  56. //| DIFF : EMA(CLOSE,S) - EMA(CLOSE,P);                             |
  57. //| DEA  : EMA(DIFF,M);                                             |
  58. //| MACD : 2*(DIFF-DEA), COLORSTICK                                 |
  59. //+------------------------------------------------------------------+
  60. int start()
  61.   {
  62.    int limit;
  63.    int counted_bars=IndicatorCounted();
  64. //---- last counted bar will be recounted
  65.    if(counted_bars>0) counted_bars--;
  66.    limit=Bars-counted_bars;
  67. //---- macd counted in the 1-st buffer
  68.    for(int i=0; i<limit; i++)
  69.       DiffBuffer[i]=iMA(NULL,0,FastEMA,0,MODE_EMA,PRICE_CLOSE,i)-iMA(NULL,0,SlowEMA,0,MODE_EMA,PRICE_CLOSE,i);
  70. //---- signal line counted in the 2-nd buffer
  71.    for(i=0; i<limit; i++)
  72.       SignalBuffer[i]=iMAOnArray(DiffBuffer,Bars,SignalSMA,0,MODE_SMA,i);
  73.    for ( i=0; i<limit; i++ )
  74.       MacdBuffer[i] = 2*(DiffBuffer[i]-SignalBuffer[i]);
  75. //---- done
  76.    return(0);
  77.   }
  78. //+------------------------------------------------------------------+
复制代码





而在一般股软里,只需要这几行:
  1. DIFF : EMA(CLOSE,S) - EMA(CLOSE,P);
  2. DEA  : EMA(DIFF,M);
  3. MACD : 2*(DIFF-DEA), COLORSTICK;
复制代码









点评

fantasynew  加深了对公式的理解  发表于 2013-12-8 23:19

使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:09:05 |显示全部楼层
言归正传,所谓“逐行模式”和“逐根模式”,就是指标引擎在背后帮用户进行循环工作时的两种不同的工作模式。

使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:09:28 |显示全部楼层
考察macd指标中的两行语句:
  1. DIFF : EMA(CLOSE,S) - EMA(CLOSE,P);
  2. DEA  : EMA(DIFF,M);
复制代码
在逐行模式和逐根模式中,它们是怎样做循环的呢?




-----------------------------------------------------------------------------------------------------------  
逐行模式
假设当前有N根K线。
    计算过程:
          计算diff的第1个元素,计算diff的第2个元素,............计算diff的第N个元素。
          计算dea的第1个元素,计算dea的第2个元素,..........计算dea的第N个元素。 
   
          新行情到来




          计算diff的第1个元素,计算diff的第2个元素,.....计算diff的第N个元素,计算diff的第N+1个元素。
          计算dea的第1个元素,计算dea的第2个元素,.....计算dea的第N个元素,计算dea的第N+1个元素。
-----------------------------------------------------------------------------------------------------------








-----------------------------------------------------------------------------------------------------------
逐根模式
计算过程:
          计算diff的第1个元素,
          计算dea的第1个元素,
          计算diff的第2个元素,
          计算dea的第2个元素,
          ............计算diff的第N个元素。
          ..........计算dea的第N个元素。




          新行情到来
          ............计算diff的第N+1个元素。
          ..........计算dea的第N+1个元素。
-----------------------------------------------------------------------------------------------------------












使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:09:53 |显示全部楼层
看到区别了吗,行模式下,每次新行情的到来,指标引擎都要把需要计算的序列从头到尾全部计算一遍。
而逐根模式下,每次新行情到来,指标引擎只计算最新一根的值。

当然,逐行模式和逐根模式还有更多的区别和适用范围。
下面再逐一解释。

使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:10:07 |显示全部楼层
本帖最后由 ptLibert 于 2012-9-19 22:29 编辑

逐根和逐行的差异

差异一:计算结果
逐行和逐根可能产生不一样的计算结果。
逐行模式,每次计算都对序列中所有元素重新计算,所以,有些情况下,某些以前计算过的值可能被修改。
也就是调用了俗称所谓“未来函数”一族函数的时候。
在这种情况下,不但调用未来函数的该行语句的序列结果会发生改变,后续语句如果用到被影响的变量,那么它们之前的值也都可能因此发生改变。

而对于逐根模式,每次计算都只计算最新一根,所以即使调用了未来函数,那么它也只改变到该函数直接影响的序列,而很可能不会将改变带给下面的计算。

差异二:计算速度
一般来说,逐行计算在K线图第一次打开时,速度要略快于逐根模式。
因为,对于很多指标,一次整行算完的话,作一些算法上的优化会比较方便。
但是,在新行情到来时,逐根计算就非常有优势了;此模式下,只计算最后一根的数值。


在测评模式下,逐根模式的速度优势可以完全的体现出来。
测评相当于一次性渐次灌入成千上万的行情。逐行的话,要对整行重复计算成千上万次,而逐根模式只需要对单根计算这么多次。
整体时间消耗的差别是几十倍上千倍的。

使用道具 举报

Rank: 8Rank: 8

发表于 2012-9-18 12:10:24 |显示全部楼层
适用范围

1、一般技术指标比较适用逐行模式。尤其是用到一些传统的未来函数时。例如,backset,zig,refx
2、交易策略指标比较适合逐根模式。

使用道具 举报

Rank: 6Rank: 6

勇士奖

发表于 2012-9-19 21:35:42 |显示全部楼层
谢谢楼主 又学习了

使用道具 举报

Rank: 6Rank: 6

激情奖

发表于 2012-10-17 15:42:37 |显示全部楼层
逐行和逐根, 在智能交易系统里都应该支持,这样才好,
很多MT4转换过来的都不支持逐根。
追求的基调是快乐投资

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

bottom

Archiver|http://www.patiosoft.com

GMT+8, 2018-11-21 13:35 , Processed in 1.031250 second(s), 11 queries .

花生网 Copyrigh©2012

和讯信息科技有限公司 ALL Rights Reserved 版权所有 复制必究

回顶部