同时运行一个以上的EA - 页 3

 
#property copyright "Copyright 2014, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict

extern bool CheckOncePerBar=true;
extern double FixedLotSize=1;
extern double SystemStopLoss=150;
extern double TakeProfit=0;
extern int Slippage=5;
extern int MagicNumber=3574;

//Global Variables
int BuyTicket=0;
int SellTicket=0;
double InternalStopLoss=0;
double CalcDigits=0;
double CalcPoint=0;
bool MABuyFanning=false;
bool MASellFanning=false;
int SelectedOrder=0;
bool Closed=false;
int ErrorCode=0;
string ErrLog="a";
double BuyStopLoss=0;
double SellStopLoss=0;
bool NewBar=false;
double ThisBarOpen=0;
double SmallMA=0;
double MediumMA=0;
double LargeMA=0;
int Counter=0;



//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
CalcDigits = MarketInfo(Symbol(),MODE_DIGITS);//MODE_DIGITS is count of digits after decimal point
if(CalcDigits==0) CalcPoint=1;//Dow      
if(CalcDigits==1) CalcPoint=0.1;   
if(CalcDigits==2) CalcPoint=0.01;//Gold & Nymex
if(CalcDigits==3) CalcPoint=0.01;//Yen
if(CalcDigits==4) CalcPoint=0.0001;//Not used
if(CalcDigits==5) CalcPoint=0.0001;//Non-Yen forex
InternalStopLoss=SystemStopLoss*CalcPoint;
   
   return(INIT_SUCCEEDED);
  }
//-----------------------------------------------

void OnTick()
{

   if(CheckOncePerBar)
      {
      if(ThisBarOpen!=Open[0])
         {
         ThisBarOpen=Open[0];
         NewBar=true;
         }
      else NewBar=false;
      }
    else NewBar=true;

if(NewBar)
{


//Reset Moving Averages
SmallMA=iMA(NULL,0,8,0,1,0,0);
MediumMA=iMA(NULL,0,10,0,1,0,0);
LargeMA=iMA(NULL,0,50,0,1,0,0);


   if(SmallMA>MediumMA&&MediumMA>LargeMA) MABuyFanning=true;
   else MABuyFanning=false;
      
   if(SmallMA<MediumMA&&MediumMA<LargeMA) MASellFanning=true; 
   else MASellFanning=false;   



if(BuyTicket==0&&MABuyFanning)
 {
      RefreshRates();
      BuyStopLoss= Bid-InternalStopLoss;
   //   while(IsTradeContextBusy()) Sleep(10);
      BuyTicket=OrderSend(Symbol(),OP_BUY,FixedLotSize,Ask,Slippage,BuyStopLoss,0,"Buy Order",MagicNumber,0,Green);
          if(BuyTicket==-1)
            {
            ErrorCode=GetLastError();
            Alert("Symbol: ",Symbol(),"Error in buy routine: ",ErrorCode);
            ErrLog=StringConcatenate("Bid: ",MarketInfo(Symbol(),MODE_BID)," Ask: ",MarketInfo(Symbol(),MODE_ASK)," Lots: ",FixedLotSize," Stop Loss: ",BuyStopLoss);
            Print(ErrLog);
            //Buy ticket revert to 0 so it can try again in case of slow connection/timeout etc.
            BuyTicket=0;
            } 
 }   


if(SellTicket==0&&MASellFanning)
 {
      RefreshRates();
      SellStopLoss=Ask+InternalStopLoss;
    //  while(IsTradeContextBusy()) Sleep(10);
      SellTicket=OrderSend(Symbol(),OP_SELL,FixedLotSize,Bid,Slippage,SellStopLoss,0,"Sell Order",MagicNumber,0,Red);
          if(SellTicket==-1)
            {
            ErrorCode=GetLastError();
            Alert("Symbol: ",Symbol(),"Error in sell routine: ",ErrorCode);
            ErrLog=StringConcatenate("Bid: ",MarketInfo(Symbol(),MODE_BID)," Ask: ",MarketInfo(Symbol(),MODE_ASK)," Lots: ",FixedLotSize," Stop Loss: ",SellStopLoss);
            Print(ErrLog);
            SellTicket=0;
            } 
  }  

//Exits

         if(BuyTicket!=0)
            {
            if(SmallMA<MediumMA)
            {
            for(Counter=0; Counter<=OrdersTotal()-1;Counter++)
               {
               SelectedOrder=OrderSelect(Counter,SELECT_BY_POS);
               if(OrderMagicNumber()==MagicNumber&&OrderSymbol()==Symbol()&&OrderType()==OP_BUY)
                  {
                 // while(IsTradeContextBusy()) Sleep(10);
                  Closed=OrderClose(OrderTicket(),OrderLots(),MarketInfo(Symbol(),MODE_BID),Slippage,Red);
                  if(Closed) BuyTicket=0;
                  else Alert("Symbol: ",Symbol()," Ticket: ",BuyTicket," unable to close buy order(s): buy ma convergence close routine");                  
                  }
            Counter--;               
                }
            }
            }

         if(SellTicket!=0)
            {
            if(SmallMA>MediumMA)
            {
            for(Counter=0;Counter<=OrdersTotal()-1;Counter++)
               {
               SelectedOrder = OrderSelect(Counter,SELECT_BY_POS);
               if(OrderMagicNumber()==MagicNumber&&OrderSymbol()==Symbol()&&OrderType()==OP_SELL)
                  {
               //   while(IsTradeContextBusy()) Sleep(10);
                  Closed=OrderClose(OrderTicket(),OrderLots(),MarketInfo(Symbol(),MODE_ASK),Slippage,Red);
                  if(Closed) SellTicket=0;
                  else Alert("Symbol: ",Symbol()," Ticket: ",SellTicket," unable to close sell order(s): sell ma convergence close routine");                  
                  }
            Counter--;               
                }
            }
            }
}            
return;   
}
 

你仍然有Counter--

见GumRai的评论https://www.mql5.com/en/forum/151167/page2#954622

 
你认为两个连续的条形图会有完全相同的开盘价吗?
   if(CheckOncePerBar){
      if(ThisBarOpen!=Open[0]){
         ThisBarOpen=Open[0];
         NewBar=true;
         }
      else NewBar=false;
      }
    else NewBar=true;

if(NewBar)
{
   : // doit
总是使用时间
static datetime ThisBarTime = 0;
if(ThisBarTime != Time[0] || !CheckOncePerBar)
{
   ThisBarTime = Time[0];
   : // doit
这不能处理deinit/init循环。外部静态变量 - MQL4论坛
 

谢谢你的帖子。

我使用Open而不是Time,因为一旦一个条形的Open发生,它就永远固定了,它永远不会改变。它不是在寻找两个连续的条形图--它是同一个条形图,并询问当前条形图的开口是否与存储在ThisBarOpen中的开口值相同。 此外,我认为Open比Time更直接,因为它是一个简单的数据查询,而Time可能需要引用其他东西,并可能进行某种计算。

关于Counter--;我没有改变这一点,因为另一个EA无法关闭订单,因为代码首先检查 MagicNumber和Symbol()是否相同。

我当然明白断电会抹去BuyTicket的内容,但这在我的测试中并没有发生,我的代码仍然运行得很慢。因此,我也看不出那会是什么原因。

我目前的主要问题是,为什么从有未结头寸的终端窗口中删除EA需要这么长的时间,而从没有未结头寸的终端中删除EA则完全没有时间。也许是巧合--但所有四个窗口都是如此?

 
上次我也遇到了同样的问题,实际上是你对EA的编码方式问题。也许现在是时候让你的EA重新从头开始写了。比如说V2。
 

我不知道这是否真的与你的问题有关,但你将你的交易限制在每个EA的1次买入和1次卖出,为什么要做这些?

  if(SellTicket!=0)
  {if(SmallMA>MediumMA)
   {for(Counter=0;Counter<=OrdersTotal()-1;Counter++)
    {SelectedOrder = OrderSelect(Counter,SELECT_BY_POS);
     if(OrderMagicNumber()==MagicNumber&&OrderSymbol()==Symbol()&&OrderType()==OP_SELL)
     {Closed=OrderClose(OrderTicket(),OrderLots(),MarketInfo(Symbol(),MODE_ASK),Slippage,Red);
      if(Closed) SellTicket=0;
      else Alert("Symbol: ",Symbol()," Ticket: ",SellTicket," unable to close sell order(s): sell ma convergence close routine");                  
     }
    Counter--;               
}}}} 

你在这里已经有了你的票据号码。

SellTicket=OrderSend(Symbol(),OP_SELL,FixedLotSize,Bid,Slippage,SellStopLoss,0,"Sell Order",MagicNumber,0,Red);

如果你把它变成一个静态的int,你就可以通过这个票号明确地关闭你的订单,而不需要在订单池中寻找它。

Closed=OrderClose(SellTicket,OrderLots(),MarketInfo(Symbol(),MODE_ASK),Slippage,Red);
 
Sneck55:

谢谢你的帖子。


关于Counter--;我没有改变,因为另一个EA无法关闭订单,因为代码首先检查MagicNumber和Symbol()是否相同。


我目前的主要问题是,为什么从终端上有未结头寸的窗口中删除EA需要这么长的时间,而从没有未结头寸的终端上删除它们则完全没有时间。也许是巧合--但所有四个窗口都是如此?


你了解循环的工作原理吗?

if(BuyTicket!=0)
            {
            if(SmallMA<MediumMA)
            {
            for(Counter=0; Counter<=OrdersTotal()-1;Counter++)
               {
               SelectedOrder=OrderSelect(Counter,SELECT_BY_POS);
               if(OrderMagicNumber()==MagicNumber&&OrderSymbol()==Symbol()&&OrderType()==OP_BUY)
                  {
                 // while(IsTradeContextBusy()) Sleep(10);
                  Closed=OrderClose(OrderTicket(),OrderLots(),MarketInfo(Symbol(),MODE_BID),Slippage,Red);
                  if(Closed) BuyTicket=0;
                  else Alert("Symbol: ",Symbol()," Ticket: ",BuyTicket," unable to close buy order(s): buy ma convergence close routine");                  
                  }
            Counter--;               
                }
            }
            }

假设你有3个未平仓的订单

在第一次运行时,计数器==0,所以指数为0的订单将被选中

在循环结束时,你将计数器减少1,所以计数器==-1。

在循环再次执行之前,作为for函数 的一部分,counter被增加1。所以counter==0

所以下一次循环的时候,counter又==0了!!如此反复。

你被困在一个无休止的循环中,不停地检查顺序索引0。

唯一停止的方法是如果没有未结订单,因为那时OrdersTotal - 1将是-1,而0并不<=-1

 
非常感谢你,GumRaj - 你已经解决了我的问题!它现在工作得很好。这是我第一次用MQL4写代码,所以这对我来说是一个学习的过程。我对for循环的工作方式感到困惑。
 
Sneck55: GumRaj - 你已经解决了我的问题!它现在工作得很好。
那你是怎么解决的呢?如果你不是在倒数,你仍然有一个问题(#3)--只是隐藏起来,直到你有多个订单或多个EA。
 
如果它关闭了一个订单,它需要递减,以配合池中发生的事情,但如果它不关闭订单,则不需要递减。如果它在没有关闭订单的情况下进行递减,就会进入一个无尽的循环。