Особенности языка mql5, тонкости и приёмы работы - страница 264

 
Nikolai Semko #:

Да, действительно, если второй параметр 1, то выделяется 8 Мб.
Если 0, то ничего не выделяется

Здесь не совсем понятно.

Сколько памяти выделять, как посчитать?

 
Vladimir Pastushak #:

Здесь не совсем понятно.

Сколько памяти выделять, как посчитать?

Логика программы должна знать заранее, сколько ячеек массиву может потребоваться. Обычно есть понимание для каждого конкретного алгоритма,  с каким шагом резервировать память. Слишком маленький шаг резерва - замедление работы программы, слишком большой - расточительство в потреблении памяти.

 
Vladimir Pastushak #:

Здесь не совсем понятно.

Сколько памяти выделять, как посчитать?

   int start_mem = TerminalInfoInteger(TERMINAL_MEMORY_USED);
   double arr[];
   ArrayResize(arr,1,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 8 Mb
   ArrayResize(arr,1,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 9 Mb
   ArrayResize(arr,1000000,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 9 Mb
   ArrayResize(arr,1000001,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 9 Mb
   ArrayResize(arr,1000002,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 16 Mb
   ArrayResize(arr,2000000,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 16 Mb
   ArrayResize(arr,2000001,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 16 Mb
   ArrayResize(arr,2000002,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 16 Mb
   ArrayResize(arr,2000003,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 24 Mb

странная картина получается.
Не понимаю, почему сначала 8, а потом 9.
А так же не понимаю, почему память расширяется второй раз при втором параметре = 1000002, а не 1000001. А в третий раз при втором параметре = 2000003, а не при 2000001 или 2000002

 
Nikolai Semko #:
А так же не понимаю, почему память расширяется второй раз при втором параметре = 1000002, а не 1000001.

Форум по трейдингу, автоматическим торговым системам и тестированию торговых стратегий

Особенности языка mql5, тонкости и приёмы работы

Nikolai Semko, 2024.06.06 01:49

   int start_mem = TerminalInfoInteger(TERMINAL_MEMORY_USED);
   double arr[];
   ArrayResize(arr,1,1e6);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 8 Mb
 

Тут физический размер 1e6 + 1, а не 1e6. То есть, 1 элемент у вас есть + 1e6 в резерве.

Резерва хватит до 1000001 включительно.

Могу ошибаться, но скорее всего не ошибаюсь

 
Vladislav Boyko #:

Тут физический размер 1e6 + 1, а не 1e6. То есть, 1 элемент у вас есть + 1e6 в резерве.

Резерва хватит до 1000001 включительно.

Могу ошибаться, но скорее всего не ошибаюсь

ошибаетесь.
т.к. минимальная шаг 1 млн., то будет корректнее такой эксперимент:

   int start_mem = TerminalInfoInteger(TERMINAL_MEMORY_USED);
   double arr[];
   ArrayResize(arr,1,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,1,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,1000000,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,1000001,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,1000002,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,2000000,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,2000001,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,10000001,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 76 Mb
   ArrayResize(arr,10000002,1e7);
   Print(string(TerminalInfoInteger(TERMINAL_MEMORY_USED)-start_mem)+" Mb");   // 153 Mb

теперь видно, что ошибаетесь

странно, почему 76 Мб, а не 80 ?!
 
Nikolai Semko #:
странно, почему 76 Мб, а не 80 ?!

Forum on trading, automated trading systems and testing trading strategies

How to find out the reserved memory of a dynamic array?

Laszlo Tormasi, 2024.01.04 08:36

Use MQLInfoInteger to get the memory used by the script directly instead terminal memory used. 

MQLInfoInteger(MQL_MEMORY_USED)
 
Nikolai Semko #:
ошибаетесь
#define _printMemUsed(text) Print(text, " = ", MQLInfoInteger(MQL_MEMORY_USED), "Mb")

void OnStart()
  {
   _printMemUsed("start");
   double arr[];
   ArrayResize(arr, 1e6);
   _printMemUsed("1e6 + 0");
   ArrayFree(arr);
   ArrayResize(arr, 1e6, 1e6);
   _printMemUsed("1e6 + 1e6");
  }
start = 0Mb
1e6 + 0 = 8Mb
1e6 + 1e6 = 16Mb

В чем разница между

ArrayResize(arr, 1e6, 1e6);

и

ArrayResize(arr, 1, 1e6);

?

Почему это должно работать по разному?

 
Vladislav Boyko #:

хмм...
но теперь картина такая. Лучше, но все равно не понятно, почему 77, а не 80

   int start_mem = MQLInfoInteger(MQL_MEMORY_USED);
   double arr[];
   ArrayResize(arr,1,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,1,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,1000000,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,1000001,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,1000002,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,2000000,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,2000001,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,10000001,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 77 Mb
   ArrayResize(arr,10000002,1e7);
   Print(string(MQLInfoInteger(MQL_MEMORY_USED)-start_mem)+" Mb");  // 154 Mb
с массивом uchar картина такая (что максимально правдоподобно):

10 Mb
11 Mb
11 Mb
11 Mb
11 Mb
11 Mb
11 Mb
11 Mb
20 Mb
а с int такая:
39 Mb
39 Mb
39 Mb
39 Mb
39 Mb
39 Mb
39 Mb
39 Mb
77 Mb
сплошные загадки
 
Nikolai Semko #:

ошибаетесь.
т.к. минимальная шаг 1 млн., то будет корректнее такой эксперимент:

теперь видно, что ошибаетесь

странно, почему 76 Мб, а не 80 ?!

Не знаю, почему для 1000001 и 1000002 у вас теперь одинаково. У меня все как ожидалось:

#define _printMemUsed(text) Print(text, " = ", MQLInfoInteger(MQL_MEMORY_USED), "Mb")

void OnStart()
  {
   _printMemUsed("start");
   double arr[];
   ArrayResize(arr, 1, 1e6);
   _printMemUsed("[1, 1e6]");
   ArrayResize(arr, 1e6 + 1, 1e6);
   _printMemUsed("[1e6 + 1, 1e6]");
   ArrayResize(arr, 1e6 + 2, 1e6);
   _printMemUsed("[1e6 + 2, 1e6]");
  }
start = 0Mb
[1, 1e6] = 8Mb
[1e6 + 1, 1e6] = 8Mb
[1e6 + 2, 1e6] = 16Mb
 
Nikolai Semko #:

хмм...
но теперь картина такая. Лучше, но все равно не понятно, почему 77, а не 80

А вы откуда запускаете? Наверное start_mem не равна нулю потому, что в программе еще что-то есть, кроме кода, который вы публикуете.

Напечатайте start_mem тоже