错误、漏洞、问题 - 页 2667

 
所以我所描述的错误并不是开发者感兴趣的,好吧...
 
MT5错误(build 2345)很长一段时间,我不明白为什么剖析器 在运行和工作,但没有任何地方显示结果。
事实证明,脚本项目的剖析器只有在禁用优化时才会显示结果,如果启用了优化,一切都在运行,可以工作,但没有任何结果。
 
Sergey Dzyublik:
我有一个MT5(build 2345)的错误,不明白为什么剖析器 在运行和工作,但没有显示结果。
事实证明,脚本项目的剖析器只有在禁用优化时才会显示结果,如果启用了优化,那么一切都会运行并工作,但没有任何结果。

剖析器对所有指标都不起作用(没有优化)。我在论坛上写了两次,在PM中把代码发给开发人员--没有答复。

 
我在MT5(build 2345)中使用分析器。
粗略地说,我想知道为什么两种算法在不同的速度下最终会得到相同的结果,在优化模式 下会有1.7倍的缩减。

#include <stl_vector.mqh>

// TickCounts: 850
vector<int>::move test_vector_move_return_assign_by_index(int n){
   vector<int> v(n);
   for(int i = 0; i < n; i++){
      v[i].UNREF  = i;
   }
   return v;
};

// TickCounts: 1450
vector<int>::move test_vector_move_return_push_back(int n){
   vector<int> v;
   // lazy implementation  
   v.reserve(n);                      
   for(int i = 0; i < n; i++){
      v.push_back(i);
   }
   return v;
};


void OnStart()
{
   for(int i = 0; i < 20000; i++){
       vector<int> v_int_move = test_vector_move_return_assign_by_index(1000);
   }
   
   for(int i = 0; i < 20000; i++){
      vector<int> v_int_move = test_vector_move_return_push_back(1000);
   }
}


因此,我们获得了使用MT5剖析器的实际经验,并发现了其操作中的一些错误。
由于不清楚开发者是否对这些信息感兴趣,也不希望花费数小时的时间来定位bug,因此将只提供检测到的问题的简要信息。

1)没有办法比较不同算法的速度。
因此,一个比其他算法快三倍的算法,无论是启用还是不启用优化,在分析器中都可能显得最慢。
显然,存在某种剖析器开销,它影响了算法的执行时间,在这种情况下,比较剖析器中算法的性能速度是没有意义的。

2)屏幕上直方图工具提示中的计数值不正确。
剖析器显示,该函数被启动了8万次,而不是预期的2万次,同样,对于不同的字符串,计数被超过了多次,一些字符串被超过了3次,另一些被超过了2次。

3) 屏幕上直方图工具提示中的时间值不正确。
有些情况下,剖析器显示算法99.90%的时间都进入了这个条件,而实际上在20K个通道中只发生了一次。

 

这不是一个错误,这更像是一个评论!


mt 5 build 2340。

昨天当我打开数据目录时,我没有注意到指标文件夹是如何被移到专家文件夹的。然后我禁用了mt5,今天启用了它,指标也可以从导航仪中使用,就像什么都没发生过一样。然而,如果我重新打开数据文件夹,会出现一个空的指标文件夹,如果我把一些指标移到其中,它将不会出现在导航仪中。它将不会出现在导航仪中。将指标文件夹返回到MQL5\Indicators解决了这个问题。

 

MT5 (build 2347)如果事先为它们预留了内存,那么在使用ArrayResize向数组中一次添加一个元素时,为什么会有这么大的开销?

#define  K 1000
#define  M (1000 * K)

#define    SpeedTest(test_count,msg,EX)        {uint mss=GetTickCount(); ulong count=test_count;for(ulong ii=0;ii<count&&!_StopFlag;ii++){EX;} \
                                              printf("%-60s: loops=%i ms=%u",msg,count,GetTickCount()-mss);}
                                              
class A{
public:
   int data;
};

struct B{
   int data;
};

template<typename T>
void test1(const int test_count, const int array_size){
   SpeedTest(
   test_count,"Test Class ArrayResize all",
   {
      T class_array[];
      for(int i = 1; i <= array_size; i++){
         ArrayResize(class_array, array_size);
      }
   }
   )
};

template<typename T>
void test2(const int test_count, const int array_size){
   SpeedTest(
   test_count,"Test Class ArrayResize one by one with reserved memory",
   {
      T class_array[];
      ArrayResize(class_array, 1, array_size - 1);
      for(int i = 2; i <= array_size; i++){
         ArrayResize(class_array, i);
      }
   }
   )
};

void OnStart()
{
  const int test_count = 5*K;
  const int array_size = 5*K;  
  
  test1<int>(test_count, array_size);            // Avg time: 100
  test2<int>(test_count, array_size);            // Avg time: 190
  test1<int>(test_count, array_size);
  test2<int>(test_count, array_size);
  test1<int>(test_count, array_size);
  test2<int>(test_count, array_size);
  test1<int>(test_count, array_size);
  test2<int>(test_count, array_size);
  
printf("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA");
  test1<A>(test_count, array_size);              // Avg time: 810
  test2<A>(test_count, array_size);              // Avg time: 1460
  test1<A>(test_count, array_size);
  test2<A>(test_count, array_size);
  test1<A>(test_count, array_size);
  test2<A>(test_count, array_size);
  test1<A>(test_count, array_size);
  test2<A>(test_count, array_size);
  
printf("BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB");
  test1<B>(test_count, array_size);              // Avg time: 110
  test2<B>(test_count, array_size);              // Avg time: 770
  test1<B>(test_count, array_size);
  test2<B>(test_count, array_size);
  test1<B>(test_count, array_size);
  test2<B>(test_count, array_size);
  test1<B>(test_count, array_size);
  test2<B>(test_count, array_size);
}

请考虑用ArrayResize改进内部保留算法。

例如,对于类,我们可以假设它们除了调用构造函数外,还执行某种 "在列表中进行内部注册 "的操作。
而在用ArrayResize保留的框架内,除了直接分配内存之外,你可以尝试优化这个过程。
- 从相邻的创建元素中获取数据(例如,指向虚拟函数 表的指针)。
- 预先执行或为尚未创建的班级的 "内部注册 "保留空间。

 
Sergey Dzyublik:

MT5 (build 2347)如果事先为它们预留了内存,那么在使用ArrayResize向数组中一次添加一个元素时,为什么会有这么大的开销?

即使这样也无济于事。

      ArrayResize(class_array, 1, array_size - 1);
      for(int i = 0; i < array_size; i++){
//         ArrayResize(class_array, i);
         ArrayResize(class_array, i, array_size - 1);

它只是没有任何意义。与其说是在加速,不如说是在减速。


ZZ 很奇怪,执行文档中的例子的 结果是零。

--- Test Fast: ArrayResize(arr,100000,100000)
1. ArraySize(arr)=100000 Time=0 ms
2. ArraySize(arr)=200000 Time=0 ms
3. ArraySize(arr)=300000 Time=0 ms
---- Test Slow: ArrayResize(slow,100000)
1. ArraySize(slow)=100000 Time=0 ms
2. ArraySize(slow)=200000 Time=0 ms
Документация по MQL5: Операции с массивами / ArrayResize
Документация по MQL5: Операции с массивами / ArrayResize
  • www.mql5.com
При успешном выполнении функция возвращает количество всех элементов, содержащихся в массиве после изменения размера; в противном случае возвращает -1 и массив не меняет размеры. Если ArrayResize() применена к статическому массиву, таймсерии или индикаторному буферу, то размер массива остается прежним – такие массивы не могут быть...
 
Sergey Dzyublik :
在MT5(build 2345)中使用剖析器工作。
粗略的说,我想知道为什么两个算法,最后给出的结果是一样的,但运行的速度却不一样,在优化模式 下的缩减是1.7倍。


...

不幸的是,这种长时间的剖析器对任何重要的项目都是无用的。我已经试图报告此事,但开发商没有兴趣。
 
Sergey Dzyublik :

MT5 (build 2347)如果事先为它们预留了内存,为什么使用ArrayResize一次向数组添加一个元素时有这么大的开销?

如果你想比较,应该是这样。

 void test1 ( const int test_count, const int array_size){
   SpeedTest(
   test_count,"Test Class ArrayResize all",
   {
      T class_array[];
       for ( int i = 0 ; i < array_size; i++){
         ArrayResize (class_array,  i );
      }
   }
   )
 
Alain Verleyen:

如果你想比较,应该是这样。

在我这边,比较的结果是它应该是这样的。
我知道有多少元素将被放置在数组中,我没有一次性创建它们,而是为未创建的元素保留内存。
问题是,如果我保留内存并一个一个地创建数组元素,需要的时间比一次性创建要长很多倍。
因此,对于结构来说,它的速度要慢7倍。
而对于类和int数据类型,它的速度要慢两倍。

这是一个非常大的区别,我相信如果开发者愿意,他们可以消除这种区别。

原因: