小额资金管理-指标被新的MQL4毁掉了

 

嘿,编码员。

我做了一个小的资金管理指标,对我来说运行良好。但自从新的MQL4之后,它引起了我无法处理的问题。

当你把这个指标拖到你的图表上时,一些数字会印在最右边。第一个数字是指以点为单位的止损,第二个数字是手的大小。在选项中,你可以选择风险。另一个数字是止损水平。但是当我改变货币对 的时候,这些数字就不见了。相反,我看到几次 "标签 "这个词。而当我看向指标列表时,我的指标也不见了。所以,总之,在改变货币对后,指标不见了,只剩下标签而不是数字。

我完全糊涂了。这个指标以前工作时没有任何问题。非常感谢您的帮助。

以下是代码。

#property indicator_chart_window
//--- input parameters
extern int  Risk=2;
extern int SL_Levels=20;
int multi, exp, SL, i, k;
double MoneyRisk, Spread, _modifySpread, lots;
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
//---- indicators
   k=0;
   for(i=1; i<=SL_Levels; i++)
   {
      if (ObjectFind("SL"+i) == -1)
      {
         ObjectCreate("SL"+i, OBJ_LABEL, 0, 0, 0);
         ObjectSet("SL"+i, OBJPROP_CORNER, 1);
         ObjectSet("SL"+i, OBJPROP_XDISTANCE, 3);
         ObjectSet("SL"+i, OBJPROP_YDISTANCE, k);
         k=k+15;    
      }
   }
   if (ObjectFind("Spread") == -1)
   {
      ObjectCreate("Spread", OBJ_LABEL, 0, 0, 0);
      ObjectSet("Spread", OBJPROP_CORNER, 3);
      ObjectSet("Spread", OBJPROP_XDISTANCE, 3);
      ObjectSet("Spread", OBJPROP_YDISTANCE, 1);
   }
   
//-- 4 / 5 Digit Settings --
   multi   = 1;
   exp     = 0;
   if (Digits==5 || Digits==3)
   {
      _modifySpread = 0.1;
      multi=10;
      exp=1;
   }
//----
   SL = MathFloor((iATR(NULL, PERIOD_D1, 7, 0)*MathPow(10,Digits-exp)+1)*0.1);
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
//----
   for(i=1; i<=SL_Levels; i++)
   {
      ObjectDelete("SL"+i);
   }
   ObjectDelete("Spread");
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
//----
   Spread     = MarketInfo(Symbol(), MODE_SPREAD)*_modifySpread;
   MoneyRisk  = AccountBalance()*Risk*0.01;
   k=0;
   for(i=1; i<=SL_Levels; i++)
   {
      lots=MoneyRisk/SL/(MarketInfo(Symbol(), MODE_TICKVALUE)*multi);
      ObjectSetText("SL"+i, SL+ " : "+DoubleToStr(lots, 2), 10, "Calibri", Red);
      k=k+15;
      SL = SL+MathFloor(((iATR(NULL, PERIOD_D1, 7, 0)*MathPow(10,Digits-exp)+1)*0.1)/2);     
   }
   SL = MathFloor((iATR(NULL, PERIOD_D1, 7, 0)*MathPow(10,Digits-exp)+1)*0.1);
   ObjectSetText("Spread", DoubleToStr(Spread,1), 10, "Calibri", Red);
   WindowRedraw();
//----
   return(0);
  }
//+------------------------------------------------------------------+
 

首先,你不能用 "exp "来表示一个int,这是保留的

其次,你表达了 "SL "的含义

SL = MathFloor((iATR(NULL, PERIOD_D1, 7, 0)*MathPow(10,Digits-exp)+1)*0.1);

在初始部分,这是个坏主意

因为如果你得到错误4066,"SL"=0

那么你就会在 "lot "上得到零除数

lots=MoneyRisk/SL/(MarketInfo(Symbol(), MODE_TICKVALUE)*multi);

指标就会停止,你必须重新加载指标。

 
我明白了。刚刚改变了变量exp,但你能告诉我如何检查 或避免错误4066吗?我读到,这与MetaTrader只更新当前图表和时间框架的报价有关。但你建议如何避免4066?
 

显然你不能避免更新;-)但你必须避免"零除法"的情况。

所以你必须检查其中一个变量是否等于0....,以避免零除法的情况。

因为你不能停止一个指标,你必须想办法。

例子。

SL = MathFloor((iATR(NULL, PERIOD_D1, 7, 0)*MathPow(10,Digits-exp)+1)*0.1);
if (SL == 0) // because error 4066 (for example)
   {
   SL = Someting;
   }
lots=MoneyRisk/SL/(MarketInfo(Symbol(), MODE_TICKVALUE)*multi);
 

你是对的。我不能回避它。)

我的意思是,我能否等到更新完成后再继续进行SL计算?问题是我不能给SL一个随机值,因为那样整个指标就没有用了。所以我想检查一下 错误4066,如果它发生了,我想等待一下,在继续之前再检查一下。

 

顺便说一下,我对这个指标也有同样的问题。但为什么在 "老 "MetaTrader中没有这个问题?在这里我总是收到ATR(5)的零。为什么?这在以前从未发生过...我讨厌这个新的MetaTrader...!

int start()
//----
  {
   double Spread = MarketInfo(Symbol(), MODE_SPREAD);
   double ATR = iATR(NULL, PERIOD_D1, 5, 0);
   int exp1 = 0;
   if (Digits==5 || Digits==3)
   {
      Spread=Spread*0.1;
      exp1 = 1;
   }
   Comment  (
            "ADR(5): ",DoubleToStr(ATR*MathPow(10,Digits-exp1),1),
            " || TODAY: ",(iHigh(NULL, PERIOD_D1, 0)-iLow(NULL, PERIOD_D1, 0))*MathPow(10,Digits-exp1),
            " || ", DoubleToStr(((iHigh(NULL, PERIOD_D1, 0)-iLow(NULL, PERIOD_D1, 0))*MathPow(10,Digits-exp1)/(ATR*MathPow(10,Digits-exp1))*100), 2), "%",
            "\n" +
            "SPREAD: ", Spread,
            " || RATIO: ",DoubleToStr((Spread/ATR)*MathPow(10,-(Digits-exp1-2)), 2),"%"
            );
//----
   return(0);
  }
 
你说的零是什么意思?我打印了所有的评论,ATR(5)显示的输出大于零......实际上是50以上......。
 

我想我找到了问题所在!这绝对是一个更新问题。当我现在改变货币时,该指标可以工作。但后来我打开了一个我今天还没有打开的货币对。然后我得到了这个消息。


打开一个你今天还没有打开的货币对。切换到你喜欢的任何时间框架,除了D1。然后你把指标拖到你的图表上。结果会出现上面那样的错误。在我看来,日线图的ATR(5)是不正确的,因为缺少DAILY数据。在D1时间框架中打开一个 "新 "图表,完全没有问题。当你切换到另一个时间框架时,它也是好的,因为ATR(5)是正确的。我注意到,只要我停留在D1图表中,我可以切换到任何货币对。但是,只要MetaTrader没有收到每日数据,在D1以外的其他时间框架中切换到其他货币对就会出现问题。 因此,我现在的问题是,当我在非D1的时间框架中打开一个新的图表时,我怎样才能得到每日数据,使我的ATR计算正确?
 

你必须把类似

if(number==0)dothis; else dothis; 

在ShowSpread.mq4中


就在发生这个零除法 的那一行进行搜索。

 
mar:

我想我找到了问题所在!这绝对是一个更新问题。当我现在改变货币时,该指标可以工作。但后来我打开了一个我今天还没有打开的货币对。然后我得到了这个消息。


打开一个你今天还没有打开的货币对。切换到你喜欢的任何时间框架,除了D1。然后你把指标拖到你的图表上。结果会出现上面那样的错误。在我看来,日线图的ATR(5)是不正确的,因为缺少DAILY数据。在D1时间框架中打开一个 "新 "图表,完全没有问题。当你切换到另一个时间框架时,它也是好的,因为ATR(5)是正确的。我注意到,只要我停留在D1图表中,我可以切换到任何货币对。但是,只要MetaTrader没有收到每日数据,在D1以外的其他时间框架中切换到其他货币对就会出现问题。因此,我现在的问题是,当我在一个非D1的时间框架内打开一个新的图表时,我怎样才能得到每日数据,使我的ATR计算正确?
qjol已经说了你的问题所在。如果你请求帮助,为什么不遵循或至少检查一下 别人给你的建议?
 

angevoyageur,我想你没有看到我发的这个帖子。

mar 2014.04.02 08:16#

你是对的...我无法回避它。 :-)

"我的意思是,我能否等到更新完成后再继续进行SL-计算?问题是我不能给SL一个随机值,因为那样整个指标就没有用了。所以我想检查一下错误4066,如果它发生了,我想等待一下,在继续之前再检查一下。"

在这里你可以看到,描述了我不能遵循建议,因为我得出了这个解决方案,你也可以看到,我肯定检查了qjol建议我的东西。