文章 "如何利用 MQL5 检测蜡烛形态" - 页 2

 
Mohamed Abdelmaaboud #:
感谢您的评论。首先,我需要澄清的是,您可以按照自己的方式来做,它可以是一个可以检测并显示它们的指标,也可以是一个可以给您提供必要操作(如交易)的 EA,如果您想要的话,您可以将它们组合成一个高级 EA。

我就是这么做的,我把所有东西都合并成了一个 EA。但当我尝试将其写成一个指标时,它在终端中仍然是作为智能交易系统加载的。代码中有些地方需要修改,但我不知道具体是什么,我知道的不多。我还注意到,它需要改进的地方是,当时间框架换成另一个时,信号会保留在图表上,而不会与新框架中相同位置的条形图相对应。理想情况下,当改变时间框架时,应该只在检测到信号的时间框架上删除或保存信号。为了以防万一,我把我收集的代码放上来,看看你能做些什么调整或优化,我只是把所有的智能交易系统复制到一个系统中,但我认为你可以在开头声明一些变量,这样就不会在代码中重复多次了。

//+------------------------------------------------------------------+
//|PATTERN-INDIK.mq5
//|版权 2023 年,维克多 | |
//|https://www.mql5.com ||
//+------------------------------------------------------------------+
#property copyright "Copyright 2023,VIKTOR"
#property link      "https://www.mql5.com"
#property version   "1.00"
#property indicator_chart_window
//+------------------------------------------------------------------+
//| 自定义指示器初始化函数
//+------------------------------------------------------------------+
//+------------------------------------------------------------------+
//+ createObj1 = Doji|
//+ createObj2 = Hammer|
//+ createObj3 = Engulfing|
//+ createObj4 = Piercing|
//+ createObj5 = Star|
//+ createObj6 = threeInside|
//+------------------------------------------------------------------+
void OnTick()
  {
   getDoji();
   getHammer(0.07,0.7);
   getEngulfing();
   getPiercing();
   getStar(0.5);
   getthreeInside();
  }
int getDoji()
  {
   datetime time  =iTime  (_Symbol,PERIOD_CURRENT,1);
   double   open  =iOpen  (_Symbol,PERIOD_CURRENT,1);
   double   high  =iHigh  (_Symbol,PERIOD_CURRENT,1);
   double   low   =iLow   (_Symbol,PERIOD_CURRENT,1);
   double   close =iClose (_Symbol,PERIOD_CURRENT,1);
   
//Doji
   if(open==close)
     {
      createObj1a(time,low,217, clrBlack,"Doji");
        {
         return 1;
        }
     }
   return 0;
  }
void createObj1a(datetime time, double price, int arrawCode, color clr, string txt)
  {
   string objName=" ";
   StringConcatenate(objName, "Signal at ",time, " at ",DoubleToString(price,_Digits)," (",arrawCode,")");
   if(ObjectCreate(0,objName,OBJ_ARROW,0,time,price))
     {
      ObjectSetInteger(0,objName,OBJPROP_ARROWCODE,arrawCode);
      ObjectSetInteger(0,objName,OBJPROP_COLOR,clr);
     }
   string candleName=objName+txt;
   if(ObjectCreate(0,candleName,OBJ_TEXT,0,time,price))
     {
      ObjectSetString(0,candleName,OBJPROP_TEXT," "+txt);
      ObjectSetInteger(0,candleName,OBJPROP_COLOR,clr);
     }
  }
//+------------------------------------------------------------------+
int getHammer(double smallShadowRatio, double longShadowRatio)
  {
//为价格数据创建变量 - 开盘价、最高价、最低价、收盘价
   datetime time=iTime(_Symbol,PERIOD_CURRENT,1);
   double open=iOpen(_Symbol,PERIOD_CURRENT,1);
   double high=iHigh(_Symbol,PERIOD_CURRENT,1);
   double low=iLow(_Symbol,PERIOD_CURRENT,1);
   double close=iClose(_Symbol,PERIOD_CURRENT,1);
   double candleSize=high-low;
//绿锤
   if(open<close)
     {
      if(high-close < candleSize*smallShadowRatio)
        {
         if(open-low>candleSize*longShadowRatio)
            createObj2(time,low,217, clrGreen,"Hammer");
           {
            return 1;
           }
        }
     }
//红色锤子
   if(open>close)
     {
      if(high-open<candleSize*smallShadowRatio)
        {
         if(close-low>candleSize*longShadowRatio)
            createObj2(time,high,218,clrRed,"Hammer");
           {
            return 1;
           }
        }
     }
//绿色反锤
   if(open<close)
     {
      if(open-low < candleSize*smallShadowRatio)
        {
         if(high-close>candleSize*longShadowRatio)
            createObj2(time,low,217, clrGreen,"Inverted Hammer");
           {
            return -1;
           }
        }
     }
//红色反锤
   if(open>close)
     {
      if(close-low < candleSize*smallShadowRatio)
        {
         if(high-open>candleSize*longShadowRatio)
            createObj2(time,high,218, clrRed,"Inverted Hammer");
           {
            return -1;
           }
        }
     }
   return 0;
  }
void createObj2(datetime time, double price, int arrawCode, color clr, string txt)
  {
   string objName=" ";
   StringConcatenate(objName, "Signal@",time, "at",DoubleToString(price,_Digits),"(",arrawCode,")");
   if(ObjectCreate(0,objName,OBJ_ARROW,0,time,price))
     {
      ObjectSetInteger(0,objName,OBJPROP_ARROWCODE,arrawCode);
      ObjectSetInteger(0,objName,OBJPROP_COLOR,clr);
      if(clr==clrGreen)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_TOP);
      if(clr==clrRed)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_BOTTOM);
     }
   string candleName=objName+txt;
   if(ObjectCreate(0,candleName,OBJ_TEXT,0,time,price))
     {
      ObjectSetString(0,candleName,OBJPROP_TEXT," "+txt);
      ObjectSetInteger(0,candleName,OBJPROP_COLOR,clr);
     }
  }
//+------------------------------------------------------------------+
int getEngulfing()
  {
   datetime time=iTime(_Symbol,PERIOD_CURRENT,1);
   double open=iOpen(_Symbol,PERIOD_CURRENT,1);
   double high=iHigh(_Symbol,PERIOD_CURRENT,1);
   double low=iLow(_Symbol,PERIOD_CURRENT,1);
   double close=iClose(_Symbol,PERIOD_CURRENT,1);
   double open2=iOpen(_Symbol,PERIOD_CURRENT,2);
   double high2=iHigh(_Symbol,PERIOD_CURRENT,2);
   double low2=iLow(_Symbol,PERIOD_CURRENT,2);
   double close2=iClose(_Symbol,PERIOD_CURRENT,2);
   if(open<close)
     {
      if(open2>close2)
        {
         if(high>high2&&low<low2)
           {
            if(close>open2&&open<close2)
              {
               createObj3(time,low,217, clrGreen,"Bullish Engulfing");
                 {
                  return 1;
                 }
              }
           }
        }
     }
   if(open>close)
     {
      if(open2<close2)
        {
         if(high>high2&&low<low2)
           {
            if(close<open2&&open>close2)
              {
               createObj3(time,high,218, clrRed,"Bearish Engulfing");
                 {
                  return -1;
                 }
              }
           }
        }
     }
   return 0;
  }
void createObj3(datetime time, double price, int arrawCode, color clr, string txt)
  {
   string objName=" ";
   StringConcatenate(objName, "Signal@",time, "at",DoubleToString(price,_Digits),"(",arrawCode,")");
   if(ObjectCreate(0,objName,OBJ_ARROW,0,time,price))
     {
      ObjectSetInteger(0,objName,OBJPROP_ARROWCODE,arrawCode);
      ObjectSetInteger(0,objName,OBJPROP_COLOR,clr);
      if(clr==clrGreen)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_TOP);
      if(clr==clrRed)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_BOTTOM);
     }
   string candleName=objName+txt;
   if(ObjectCreate(0,candleName,OBJ_TEXT,0,time,price))
     {
      ObjectSetString(0,candleName,OBJPROP_TEXT," "+txt);
      ObjectSetInteger(0,candleName,OBJPROP_COLOR,clr);
     }
  }
//+------------------------------------------------------------------+
int getPiercing()
  {
   datetime time=iTime(_Symbol,PERIOD_CURRENT,1);
   double open=iOpen(_Symbol,PERIOD_CURRENT,1);
   double high=iHigh(_Symbol,PERIOD_CURRENT,1);
   double low=iLow(_Symbol,PERIOD_CURRENT,1);
   double close=iClose(_Symbol,PERIOD_CURRENT,1);
   double open2=iOpen(_Symbol,PERIOD_CURRENT,2);
   double high2=iHigh(_Symbol,PERIOD_CURRENT,2);
   double low2=iLow(_Symbol,PERIOD_CURRENT,2);
   double close2=iClose(_Symbol,PERIOD_CURRENT,2);
   double candleSize2=high2-low2;
   double candleMidPoint2=high2-(candleSize2/2);
   if(open<close)
     {
      if(open2>close2)
        {
         if(open<low2)
           {
            if(close>candleMidPoint2&&close<high2)
              {
               createObj4(time,low,217, clrGreen,"Piercing");
                 {
                  return 1;
                 }
              }
           }
        }
     }
   if(open>close)
     {
      if(open2<close2)
        {
         if(open>high2)
           {
            if(close<candleMidPoint2&&close>low2)
              {
               createObj4(time,high,218, clrRed,"Dark Cloud");
                 {
                  return -1;
                 }
              }
           }
        }
     }
   return 0;
  }
void createObj4(datetime time, double price, int arrawCode, color clr, string txt)
  {
   string objName=" ";
   StringConcatenate(objName, "Signal@",time, "at",DoubleToString(price,_Digits),"(",arrawCode,")");
   if(ObjectCreate(0,objName,OBJ_ARROW,0,time,price))
     {
      ObjectSetInteger(0,objName,OBJPROP_ARROWCODE,arrawCode);
      ObjectSetInteger(0,objName,OBJPROP_COLOR,clr);
      if(clr==clrGreen)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_TOP);
      if(clr==clrRed)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_BOTTOM);
     }
   string candleName=objName+txt;
   if(ObjectCreate(0,candleName,OBJ_TEXT,0,time,price))
     {
      ObjectSetString(0,candleName,OBJPROP_TEXT," "+txt);
      ObjectSetInteger(0,candleName,OBJPROP_COLOR,clr);
     }
  }
//+------------------------------------------------------------------+
int getStar(double middleCandleRatio)
  {
   datetime time=iTime(_Symbol,PERIOD_CURRENT,1);
   double open=iOpen(_Symbol,PERIOD_CURRENT,1);
   double high=iHigh(_Symbol,PERIOD_CURRENT,1);
   double low=iLow(_Symbol,PERIOD_CURRENT,1);
   double close=iClose(_Symbol,PERIOD_CURRENT,1);
   double open2=iOpen(_Symbol,PERIOD_CURRENT,2);
   double high2=iHigh(_Symbol,PERIOD_CURRENT,2);
   double low2=iLow(_Symbol,PERIOD_CURRENT,2);
   double close2=iClose(_Symbol,PERIOD_CURRENT,2);
   double open3=iOpen(_Symbol,PERIOD_CURRENT,3);
   double high3=iHigh(_Symbol,PERIOD_CURRENT,3);
   double low3=iLow(_Symbol,PERIOD_CURRENT,3);
   double close3=iClose(_Symbol,PERIOD_CURRENT,3);
   double candleSize=high-low;
   double candleSize2=high2-low2;
   double candleSize3=high3-low3;
   if(open<close)
     {
      if(open3>close3)
        {
         if(candleSize2<candleSize*middleCandleRatio && candleSize2<candleSize3*middleCandleRatio)
           {
            createObj5(time,low,217, clrGreen,"Morning Star");
              {
               return 1;
              }
           }
        }
     }
   if(open>close)
     {
      if(open3<close3)
        {
         if(candleSize2<candleSize*middleCandleRatio && candleSize2<candleSize3*middleCandleRatio)
           {
            createObj5(time,high,218, clrRed,"Evening Star");
              {
               return -1;
              }
           }
        }
     }
   return 0;
  }
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
void createObj5(datetime time, double price, int arrawCode, color clr, string txt)
  {
   string objName=" ";
   StringConcatenate(objName, "Signal@",time, "at",DoubleToString(price,_Digits),"(",arrawCode,")");
   if(ObjectCreate(0,objName,OBJ_ARROW,0,time,price))
     {
      ObjectSetInteger(0,objName,OBJPROP_ARROWCODE,arrawCode);
      ObjectSetInteger(0,objName,OBJPROP_COLOR,clr);
      if(clr==clrGreen)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_TOP);
      if(clr==clrRed)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_BOTTOM);
     }
   string candleName=objName+txt;
   if(ObjectCreate(0,candleName,OBJ_TEXT,0,time,price))
     {
      ObjectSetString(0,candleName,OBJPROP_TEXT," "+txt);
      ObjectSetInteger(0,candleName,OBJPROP_COLOR,clr);
     }
  }
//+------------------------------------------------------------------+
int getthreeInside()
  {
   datetime time=iTime(_Symbol,PERIOD_CURRENT,1);
   double open=iOpen(_Symbol,PERIOD_CURRENT,1);
   double high=iHigh(_Symbol,PERIOD_CURRENT,1);
   double low=iLow(_Symbol,PERIOD_CURRENT,1);
   double close=iClose(_Symbol,PERIOD_CURRENT,1);
   double open2=iOpen(_Symbol,PERIOD_CURRENT,2);
   double high2=iHigh(_Symbol,PERIOD_CURRENT,2);
   double low2=iLow(_Symbol,PERIOD_CURRENT,2);
   double close2=iClose(_Symbol,PERIOD_CURRENT,2);
   double open3=iOpen(_Symbol,PERIOD_CURRENT,3);
   double high3=iHigh(_Symbol,PERIOD_CURRENT,3);
   double low3=iLow(_Symbol,PERIOD_CURRENT,3);
   double close3=iClose(_Symbol,PERIOD_CURRENT,3);
   if(open3>close3)
     {
      if(open2<close2)
        {
         if(open2>low3&&close2<high3)
           {
            if(open<close&&open>open2&&open<close2)
              {
               if(close>high3)
                 {
                  createObj6(time,low,217, clrGreen,"3 Inside Up");
                    {
                     return 1;
                    }
                 }
              }
           }
        }
     }
   if(open3<close3)
     {
      if(open2>close2)
        {
         if(open2<high3&&close2>low3)
           {
            if(open>close&&open<open2&&open>close2)
              {
               if(close<low3)
                 {
                  createObj6(time,high,218, clrRed,"3 Inside Down");
                    {
                     return -1;
                    }
                 }
              }
           }
        }
     }
   return 0;
  }
void createObj6(datetime time, double price, int arrawCode, color clr, string txt)
  {
   string objName=" ";
   StringConcatenate(objName, "Signal@",time, "at",DoubleToString(price,_Digits),"(",arrawCode,")");
   if(ObjectCreate(0,objName,OBJ_ARROW,0,time,price))
     {
      ObjectSetInteger(0,objName,OBJPROP_ARROWCODE,arrawCode);
      ObjectSetInteger(0,objName,OBJPROP_COLOR,clr);
      if(clr==clrGreen)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_TOP);
      if(clr==clrRed)
         ObjectSetInteger(0,objName,OBJPROP_ANCHOR,ANCHOR_BOTTOM);
     }
   string candleName=objName+txt;
   if(ObjectCreate(0,candleName,OBJ_TEXT,0,time,price))
     {
      ObjectSetString(0,candleName,OBJPROP_TEXT," "+txt);
      ObjectSetInteger(0,candleName,OBJPROP_COLOR,clr);
     }
  }
//+------------------------------------------------------------------+
 
FINANSE-BOND #:

我这样做了,将它们全部合并为一个 EA。但当我尝试把它写成一个 "指标 "时,它在终端中仍然是作为 "智能交易系统 "加载的。代码中有些地方需要修改,但我不知道是什么原因,我对它了解不多。我还注意到,它需要改进的地方是,当时间框架换成另一个时,信号仍然保留在图表上,并不与新框架中相同位置的条形图相对应。理想情况下,当改变时间框架时,应该只在检测到信号的时间框架上删除或保存信号。为了以防万一,我把我收集的代码放上来,看看你能做些什么调整或优化,我只是把所有的智能交易系统复制到一个系统中,但我认为你可以在开头声明一些变量,这样就不会在代码中重复多次了。

智能交易系统和指标的不同之处仅在于它们的事件处理程序略有不同,而且当涉及到蜡烛图形态时,指标可以在图表本身或单独的窗口中绘制线条,这类代码在其他情况下完全是多余的,而且这些步骤只会限制代码的可能性。在这里,你需要正确的指标构建范例,我很早以前就意识到了这一点,而且我几乎从不编写指标,而是以智能交易系统的形式执行所有操作。此外,这段代码很容易适应未来的交易,如果你仔细看代码,就会发现其中有对象的工作,那么你为什么要把自己局限在指标的功能上呢?你正在挖掘一个人的思想,这是正确的。

 

我没有说到点子上,我写道,我在代码方面不是很强,这就是为什么我作为用户分享了我的结论,还要求在代码中删掉一点东西,我不知道在哪里以及如何声明一些重复的变量。最近还看了一个视频,他们在外部指标上编写了一个智能交易系统。这就是为什么我说如果你做了一个指标,那么你就可以在 Expert Advisor 中引用它并从中获取数据。如果可以的话,或许您可以纠正一下?

 
如果有人不偷懒,请在代码中添加买入和卖出指令,因为这是一个 Expert Advisor。
 
非常有用
 
Cyril Bassey #:
非常有帮助

感谢您的评论。

 
谢谢您的见解,非常好的帖子。
,我想知道关于探测吞没烛台的问题,您使用了
这一条件来探测看涨吞没烛台,以及使用 这一条件来探测看跌吞没烛台。
if(close>open2&&open<close2)
用于看涨吞没,
用于看跌吞没。
if(close<open2&&open>close2)
用于看跌吞没。这些条件只有在出现缺口时才成立。我是说缺口出现的频率有多高?我希望使用这样的代码
if(close>open2&&open<=close2)
用于看涨吞没,条件
if(close<open2&&open>=close2)
表示看跌吞没。因为在正常情况下,条形图 1 的开盘价和条形图 2 的收盘价 完全相同。您的代码只有在出现市场价格缺口时才会检测到吞没形态。
所以我的问题是,您认为当 Bar 2 和 Bar 1 的收盘价和开盘价不同时,形态是否会失效?
 
好文章。它对了解如何在 mql5 中创建对象 模式很有帮助。
 

非常感谢。

看涨和看跌丸红的条件是什么?

 
Sylvanus Phillips #:
看涨和看跌丸红的条件是什么?

类似这样: