我的EA做了一个重复输入 - 页 4

 
doshur:

我可以问一下PositionSelect()是检查客户端还是服务器端吗?

我有一种强烈的感觉,这个问题是由服务器(经纪商)正在处理请求而没有更新客户端的延迟造成的,这就是为什么PositionSelect()会再次运行的原因。

我强烈地感觉到,当我们使用cTrade和MqlTradeRequest 的方式时,没有任何区别,睡眠功能应该有助于延迟一切,使我们的客户端在PositionSelect()再次运行之前得到 "更新",从而导致重复输入。从我的日志标签检查, >2013.12.20 08:35:00 Trades '800****': exchange buy 0.01 EURUSD at market placed for execution in 313 ms <

把睡眠超过400应该是安全的?

你怎么看?


"我有一种强烈的感觉,这个问题是由服务器(经纪商)处理请求而没有更新客户端的延迟造成的,这就是为什么PositionSelect()再次运行的原因"

我也认为这就是重复输入的原因。在我的代码中,如果当前头寸大小等于或大于允许的最大头寸大小,理论上是不可能发送新订单的,所以当PositionSelect()没有及时收到当前头寸的状态时,我的EA会再次发送新订单。


"把睡眠超过400应该是安全的吗?"?

时间间隔越大越好,但有一个问题。如果你分两步调转你的头寸(长线转短线或短线转长线),这个额外的时间延迟可能是导致执行价格不佳的原因,特别是在宏观经济事件期间。

 
snelle_moda:


"我有一种强烈的感觉,这个问题是由服务器(经纪方)处理请求而没有更新客户端的延迟造成的,这就是为什么PositionSelect()会再次运行"

我也认为这就是重复输入的原因。在我的代码中,如果当前头寸大小等于或大于允许的最大头寸大小,理论上是不可能发送新订单的,所以当PositionSelect()没有及时收到当前头寸的状态时,我的EA会再次发送新订单。


"把睡眠时间超过400应该是安全的?

时间间隔越大越好,但有一个问题。如果你分两步调转你的头寸(长线转短线或短线转长线),这个额外的时间延迟可能是导致执行价格不佳的原因,特别是在宏观经济事件期间。

我认为这不应该是一个问题。我的EA在我刚发出买入/卖出请求时不会立即逆转。我把睡眠时间调到800ms,这样我的EA就有充足的时间来等待经纪人的更新。希望睡眠能在这里解决这个问题。
 
doshur:
我不知道经纪人是否在这里发挥了作用,但似乎我们的经纪人是一样的。阿尔帕里。

如果需要,请删除经纪人的名字。
是的,经纪人是相同的。
 
snelle_moda:


自2013年3月10日以来,我又有一次重复输入。我使用两种方法发送我的订单。见我以前的帖子。

啊哈......正如我所料......。
 

这是我刚刚实施的,希望能解决这个问题。

if(m_Trade.PositionOpen(Symbol(), ORDER_TYPE_BUY, LotSize, Price, 0, 0))
            {
               Sleep(800);

               if(m_Trade.ResultRetcode() == 10009)
               {
                  Print("Position opened in ", Symbol());

                  return;
               }
               else
               {
                  Print("Error opening position in ", Symbol(), " - ", m_Trade.ResultComment(), "\n", "Return Code Desc - ", m_Trade.ResultRetcodeDescription());
               }
            }
            else
            {
               Print("Error with PositionOpen in ", Symbol(), " - ", m_Trade.ResultComment(), "\n", "Return Code Desc - ", m_Trade.ResultRetcodeDescription());
            }
 
doshur:

这是我刚刚实施的,希望能解决这个问题。

据我所知,结果代码=10008也是表明交易的位置很好。
 

我认为找到这个问题背后的原因是非常重要的,当然,在我们能够完全理解发生了什么之前,有一个变通的办法也是非常重要的(睡眠?所以我试着恢复一下情况。

  • 当使用CTrade类的PositionOpen方法时,至少有3个用户在某些时候得到了2个相同方向的交易,而不是1个,导致相对于预期的交易量增加了一倍。
  • 最初由doshur发布的代码,可以解释为什么他可以在日志中看到 "Position opened in... "而没有交易被打开。这是因为,即使PositionOpen()返回true,也不意味着交易已经完成。见文档。但它不能解释为什么会有一个 "双倍 "交易。
  • 对于这种 "双重 "交易,我只能看到两种解释。
  1. PositionSelect()并不总是返回仓位的真实情况。一个仓位被打开了,但PositionSelect返回错误。那就是PositionSelect的问题了。
  2. 一个交易被放置,但是当PositionSelect()在下一个tick被调用时,这个头寸还不存在。为了理解这是否可能,我们必须知道交易发生时的操作流程。
  • 这个问题似乎发生在同一个经纪人身上,在一个激活了市场深度的符号上(请相关人员确认)。
  • 这个问题发生在同步订单上,没有使用异步订单(请确认)。
  • 这个问题是随机发生的。
  • Klammeraffe报告说不再 这个问题,但我看不出他发布的代码如何解释这个问题。这段代码是在每个点上执行的吗?这段代码是在使用PositionSelect()后执行的吗?所以也许他删除了错误的原因,或者这只是随机的。
  • 在检查了代码后,我看不出直接使用CTALO类或MqlTradeRequest与OrderSend有什么区别。

我同意snella_moda的观点,最好的解释是

I think the problem is the (to slow) execution of the PositionSelect(Symbol()) function. Maybe, the new ticks come in so fast, the EA sends in a new order before it receives a response of the PositionSelect(Symbol()). So the current position size is not calculated properly. In my code, its theoretically impossible to send in a new/double order if the current position size is equal or greater than the max allowed position size, see code. 

但这很难检查。

我认为最好的办法是征求Metaquotes的意见。我将尝试这样做。

 
angevoyageur:
  • Klammeraffe报告说不再 这个问题了,但我看不出他发布的代码如何解释这个问题。这段代码是在每个tick上执行的吗?这段代码是在使用PositionSelect()后执行的吗?所以,也许他删除了错误的原因,或者只是随机的。

关于 "每个tick "的那一行可能是它不再发生的原因。

函数 只在新的条形图出现时执行。因此,最可能的是,只有条形图的第一个刻度可以执行交易。在第一个条形图之后,代码得到一个 "返回",直到新条形图出现。也许这对我来说已经解决了问题。

我认为这段代码来自文章。

//-------------------------------------------------- Check for new bar     
         static datetime OldTime;
         datetime NewTime[1];
         bool newBar=false;
         
         int copied=CopyTime(Symbol(),Period(),0,1,NewTime);
         if (copied>0)
           {
             if (OldTime != NewTime[0])
               {  
                 newBar=true;
                 OldTime=NewTime[0];
               }
           }
         else
           {
            Print("Error in copying historical times data, error =",GetLastError());
            ResetLastError();
            return;
           }  
         if(newBar==false) return;      
//-------------------------------------------------- Check for new bar
 
Klammeraffe:

关于"每个tick " 的那一行可能是它不再发生的原因。

只有当一个新的柱状体出现时,该函数才会被执行。因此,最有可能的是,只有条形图的第一个刻度可以执行交易。在第一个条形图之后,代码得到一个 "返回",直到新条形图出现。也许这对我来说已经解决了问题。

我认为这段代码是来自文章。

是的,我想是的。谢谢你。
 
  • 最初由doshur发布的代码,可以解释为什么他可以在日志中看到 "Position opened in... "而没有交易被打开。这是因为,即使PositionOpen()返回true,也不意味着交易已经进行。见文档。但它不能解释为什么 "双倍 "的交易被放置。

更正。有一个双倍的"Position opened in... "和2个交易已经被打开。

  • 这个问题似乎发生在同一个经纪人身上,在一个激活了市场深度的符号上(请相关人员确认这一点)。
不确定其他人的情况,但我的确实有DOM

  • 这个问题发生在同步订单上,没有使用异步订单(请确认)。
我在使用默认的cTrade设置。

  • 这个问题是随机发生的。
是的,随机的