MT5 and speed in action - page 46

 
Renat Fatkhullin:

The millisecond timer has been around for a long time: EventSetMillisecondTimer()

You are completely out of the loop. Suppose you need to open two positions in OnTick. The first OrderSend is a few milliseconds. After it you need to make a snapshot. And then the second OrderSend should be called.

Only OnTick can be executed for hundreds of milliseconds. And you suggest to snapshot some OnTimer.

 
Renat Fatkhullin:

There are also issues with the metering library itself. There is a lot of unnecessary stuff, including the overhead.

Arguments in the studio!

 
Renat Fatkhullin:

Here's my code and stable runtime: no hundreds or thousands of microseconds on 20 graphs in parallel

How many cores do you have and what kind of processor? i7-2600?

8 cores.

2020.10.06 02:27:59.464 Terminal        MetaTrader 5 x64 build 2630 started for MetaQuotes Software Corp.
2020.10.06 02:27:59.465 Terminal        Windows 10 build 19042, Intel Core i7-2700 K  @ 3.50 GHz, 7 / 15 Gb memory, 19 / 29 Gb disk, IE 11, Admin, GMT+3

Hidden stress test again with millions of requests in parallel?

Told you many times that combat advisor. Minimized the number of calls as much as possible. In theory (I haven't measured it) up to 10 calls per OnTick.


Be more transparent. Just because you posted a couple of simple _B calls is not proof of your other claims. You abruptly forget about the code and the actual description of the conditions as soon as you make outlandish claims.

You don't need to imagine anything in your mind - tell and show what you actually call and test. Not a torn out result of "ran an unknown stress test and waiting for an alert to show the world", but exactly the full code of the test.

I'm publishing the results from the live EA. There are 70 mqh files there, including WinAPI. If you really understand it and not just words, I will give you the source code. You will reproduce the brakes pretty quickly.

 
fxsaber:

You are completely out of the loop. Let's say you need to open two positions in OnTick. The first OrderSend is a few milliseconds. After it you need to make a snapshot. And then the second OrderSend should be called.

Only OnTick can be executed for hundreds of milliseconds. And you suggest to snapshot some OnTimer.

I didn't suggest snapping, I answered a direct question about millisecond timer.

It is there, although in current tester it is still triggered at 1 sec. In the new tester we are writing, we will try to change this.
 
fxsaber:

8 cores.

Many times said combat advisor. Minimized the number of calls as much as possible. In theory (I haven't measured it) up to 10 calls per OnTick.


I am publishing the results from the Expert Advisor. There are 70 mqh files there, including WinAPI. If you don't just talk about it, but really understand it, I will give you the source code. You'll play the brakes pretty quickly.

We'll figure it out, give us the source code.
 
fxsaber:

Arguments on the table!

Your whole benchmark is overloaded with rubbish and in fact here is a clean and understandable (unlike your clutter of code) version of it:


//--- benchmark macros
#define _B(_function,_alert_interval)               \
          {                                         \
           ulong _latency=GetMicrosecondCount();    \
           _function;                               \
           _latency=GetMicrosecondCount()-_latency; \
           if(_latency > _alert_interval)           \
              ::Alert("Time[" + __FILE__ + " " + (string)__LINE__ + " in " + __FUNCTION__+ ": " + #_function + "] = " + (string)_latency + " mсs"); \
          }



//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
void OnTick()
  {
   MqlTick Tick;
   
   _B(SymbolInfoTick(_Symbol,Tick),0);
   _B(SymbolInfoTick(_Symbol,Tick),0);
  }

What are your problems:

  1. unreadable code

  2. Binding into a class with a lot of overhead

  3. the cost of storing 50 results in the stack
      static bool Set( const string Str )
      {
        if (BENCHMARK::Amount == BENCHMARK::ReserveSize)
          BENCHMARK::ReserveSize = ::ArrayResize(BENCHMARK::Bench, BENCHMARK::ReserveSize + BENCHMARK_RESERVE);
    
        BENCHMARK::Bench[BENCHMARK::Amount++].Set(Str);
    
        return(true);
      }
    
  4. taking results - one solid overhead and rubbish in object bindings
      static ulong Get( const uint AlertInterval = 0 )
      {
        const int Pos = BENCHMARK::Amount - 1;
        const ulong Res = (Pos < 0) ? 0 : BENCHMARK::Bench[Pos].Get();
    
        if (Pos >= 0)
        {
          if (AlertInterval && (Res > AlertInterval))
            ::Alert("Time[" + BENCHMARK::Bench[Pos].Str + "] = " + (string)Res + " mсs.");
    
          BENCHMARK::Amount = Pos;
        }
    
        return(Res);
      }
    


I hope you didn't disable code optimization for tests?

I mean the global parameter Optimize=0 in metaeditor.ini

 
Renat Fatkhullin:

Your whole benchmark is overloaded with rubbish and in fact here is a clean and understandable (in contrast to your clutter of code) version of it:

Your version is, unfortunately, at the early stage of understanding convenience. Convenient is when you can do it like this.

Forum on trading, automated trading systems and strategy testing

Libraries: Benchmark

fxsaber, 2020.10.01 23:49

Now we try to find out where the hiccup is in the standard variant. We add some symbols to the source code.

    for (long Chart = _B2(::ChartFirst()); (Chart != -1) && !Res; Chart = _B2(::ChartNext(Chart)))
      Res = (Chart != chartID) && _B2(::ChartGetInteger(Chart, CHART_IS_MAXIMIZED));

And immediately see the reason.

2020.10.02 00:45:14.113 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 878 mсs.
2020.10.02 00:45:14.114 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 943 mсs.
2020.10.02 00:45:14.114 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 297 mсs.
2020.10.02 00:45:14.116 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 1787 mсs.
2020.10.02 00:45:14.116 Alert: Time[Test9.mq5 35 in IsInvisible: ::ChartNext(Chart)] = 2 mсs.
2020.10.02 00:45:14.117 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 980 mсs.
2020.10.02 00:45:14.117 Alert: Time[Test9.mq5 35 in IsInvisible: ::ChartNext(Chart)] = 2 mсs.
2020.10.02 00:45:14.117 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 59 mсs.
2020.10.02 00:45:14.118 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 803 mсs.
2020.10.02 00:45:14.119 Alert: Time[Test9.mq5 36 in IsInvisible: ::ChartGetInteger(Chart,CHART_IS_MAXIMIZED)] = 1059 mсs.

CHART_IS_MAXIMIZED is too slow for someone else's charts. Bug report is ready! It was very easy with the library.


What's the problem:

  1. unreadable code

  2. strapping into a class with a lot of overhead

  3. stack storage cost of 50 results
  4. getting results - one massive overhead and rubbish in object bindings

The usability overrides the meager overhead. It's miserable if you look closely at how it's implemented. For example, ArrayResize is an overhead, so its use is minimized.

I hope you haven't disabled code optimization for tests?

I mean the global parameter Optimize=0 in metaeditor.ini

Not interested in slow modes. I'm looking at combat EA performance, paying attention to algorithmic optimization and compiler optimization as well, of course.

 
Renat Fatkhullin:

Your whole benchmark is overloaded with rubbish and in fact here is a clean and understandable (unlike your clutter of code) version of it:

What's your problem:

  1. unreadable code

  2. tying into a class with a lot of overhead

  3. stack storage cost of 50 results
  4. fetching results - all overhead and rubbish in object bindings


I hope you didn't disable code optimization for tests?

I mean the global parameter Optimize=0 in metaeditor.ini

Here it is C-style, it's simple and really rubbish free. Thanks for the example.

One of C language teachers recommended better not to use underscore _B in user names
Because this prefix is used by developers of libraries, programs, etc.
And not to run into overlap, he recommended better not to use it.

In mql5 is it possible to overlap with your names?
Or custom names are completely shielded from MQ names ?

 
Roman:

One of the C teachers recommended not to use the underscore _B in user names
, because this prefix is used by developers of libraries, software, etc.
And to avoid overlap, he recommended not to use it.

In C, names starting with "_" are used as service, system or special names. In this case, I think it's acceptable. Since this function is used for code maintenance and examination.

 
Edgar Akhmadeev:

Names beginning with "_" are used in C as service, system or special names. In this case - acceptable, I think. Since this function is used for code maintenance and examination.

That's the point, besides mql5, there are developer's MQ service names.