繁体   English   中英

如何使MQL4代码在交易上下文的实际状态下工作?

[英]How to get MQL4 code work under an actual state of a Trade context?

在以下情况下, TradeContext()有何关系?

同时发送交易指令时,在这些情况下, TradeContext()返回繁忙状态?

1)当相同的EA附加到不同的十字架上时,每个在其MetaTrader Terminal 4平台的相同实例中的自己的图表上。

2)在MetaTrader Terminal 4平台的一个实例中,采用不同策略,跨不同图表,但全部使用相同FX-cross的情况。

3)当使用MetaTrader Terminal 4平台的多个实例时,请在上述两种情况下操作EA代码。

情况3)具有更好的客户端-服务器吞吐量 ,因为MT4终端平台的每个实例都包含其自己的内部引擎(“交易(管理)上下文”实例)。 从技术上讲,此内部引擎对于用户是不可见的,但是当此引擎阻止XTO指示在服务器端实现时,用户有责任检查情况。


事实1:平台在发展。

早些年,MetaTrader Terminal 4平台经常报告案例,这是内部实施的贸易管理工厂模式的内部状态,避免了任何进一步的请求被处理。

在代码尝试检查GetLastError()_LastError或通过IsTradeContextBusy()值检查代码之后,此类指示不是异步报告的,也不与MQL4代码执行流程_LastError ,而只能间接访问:

#include <stdlib.mqh>
#include <stderror.mqh>
...
ErrorDescription( GetLastError() ); // was available for showing an Error state

并在_LastError == 146情况下
== ERR_TRADE_CONTEXT_BUSY报告交易上下文繁忙时的状态。

换句话说,工作流中的每个XTO操作通常都被仔细的错误状态检测分析代码包围,并且包括(以某种可行的形式,在可能的情况下)某种补救措施,从而克服了被阻止(拒绝)的问题。 )XTO操作,直到可能或有一些超时的看门狗控制的退出路径。

几年之后,也许是在Build 509之后,肯定是在Build 624+部署之后,这种常见(隐藏)的阻塞状态不再如此频繁地出现。

如果您观察到情况,当_LastError确实再次报告ERR_TRADE_CONTEXT_BUSY时,将需要更多注意以隔离这种状态,因此最好对代码执行流程中的所有步骤进行详细记录,以便进行映射实际平台状态。

switch( Error )
{  case ...

   case ERR_TRADE_CONTEXT_BUSY:    {  // ERR_TRADE_CONTEXT_BUSY
                                         aLogSTRING     = StringConcatenate( msLIB.anElapsedTimeSTRING(), "[ ", DoubleToStr( GetTickCount(), 0 ), " ] Trying to OrderModify() aPendingOrderOBJECT for this SONAR_BEEP Monitor at MT4Server side. <localhost>MT4Terminal reports: [ERR_TRADE_CONTEXT_BUSY] <state>. Will Sleep() here a bit more." );
                                         aComment.ADD(            aLogSTRING );
                                         aMXact.aDeferredLOGGER(  aLogSTRING, TRUE );
                                         Sleep( 60 * 1000 );
                                         break;
                                      }
   ...
   default:                        {    ...
                                      }
   }

如果无法解决这种情况的测试持续时间,则可以使用以下方法:

  while (  !IsStopped() )  {                   // LOOP FOREVER, UNTIL IsStopped()
           tix.START = GetTickCount();         // STO()_______pre-STORE()_________________________ .START
           if (  IsTradeContextBusy() ) {      // if BUSY().......MEASURE......................... .START inner-LOOP
                 while (  IsTradeContextBusy() && !IsStopped() )  {       // LOOP @BUSY()_________________________________________________________________________ tix
                          Sleep( msLIB.RT.LOOP_inMeasureSleep.ms );       //             Sleep(*)
                       }  // .............................................// LOOP .or. !BUSY()--------------------------------------------------------<_LOOP_>----     .or. { !IsTradeContextBusy() | IsStopped() }
                 tix.END    = GetTickCount();  //  STO()__________________ .END   inner-LOOP _____________________________________________________________________ tix
                 tix.BUSY   = tix.END - tix.START;
              // aString2LOG= StringConcatenate(   TimeToStr( TimeCurrent(), _time2str.MASK ),";", DoubleToStr( tix.START, 0 ), ";",  DoubleToStr( tix.BUSY, 0 ) );
                 aString2LOG= StringConcatenate(   TimeToStr( TimeLocal(),   _time2str.MASK ),";", DoubleToStr( tix.START, 0 ), ";",  DoubleToStr( tix.BUSY, 0 ) );        // TimeLocal() works either before/after Market Closes and no quotes arrive ( thus avoiding the hanging at TimeCurrent() at the time of the last known Quote.... )
              // LOG.append
              // LOG ------------------------|||||||||||||||--------------------------   
                                      aMXact.aDeferredLOGGER( aString2LOG, ( IsStopped() ) );
                 aComment.ADD( StringConcatenate(    msLIB.anElapsedTimeSTRING(),
                                                     " <localhost>.<aTradingCONTEXT>.BUSY was <OBSERVED> at ",
                                                     DoubleToStr( aLoopCOUNTER.RollOVER * msLIB.RT.LOOP_nLoops2ShowGuiMSG + aLoopCOUNTER, 0 ),
                                                     " loop, < cpuClockTIXs.START | cpuClockTIXs.DURATION> ",
                                                     aString2LOG
                                                  )
                             );
                 aLoopCOUNTER.RollOVER = 0;
                 aLoopCOUNTER = 0;
              }

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM