В MQL4 я мог бы использовать следующую функцию для вывода значений из двумерного массива:
string Arr2ToString(double& arr[][], string dlm = ",", int digits = 2) {
string res = "";
int i, j;
for (i = 0; i < ArrayRange(arr, 0); i++) {
res += "[";
for (j = 0; j < ArrayRange(arr, 1); j++) {
res += StringFormat("%g%s", NormalizeDouble(arr[i][j], digits), dlm);
}
res = StringSubstr(res, 0, StringLen(res) - StringLen(dlm));
res += "]" + dlm;
}
res = StringSubstr(res, 0, StringLen(res) - StringLen(dlm));
return res;
}
Однако в MQL5 (версия 5.00, сборка 1966) вышеуказанная функция больше не работает и выдает ошибку:
'[' - invalid index value Array.mqh
в первой строке, когда передается arr[][]
.
Я проверил, и MQL5 больше не позволяет передавать массив без размерности.
When passing multidimensional arrays to a function, dimension sizes (except for the first one) should be specified:
double var[][3][3]; void Func(double &arg[][3][3]){ // ... }
Источник: ОСНОВЫ ПРОГРАММИРОВАНИЯ MQL5: МАССИВЫ.
Это не имеет смысла.
Предполагая, что я не знаю размер своего массива (поскольку я хочу повторно использовать эту функцию для нескольких типов массивов, и определение десятков отдельных функций для каждого размера нелепо), как теперь можно печатать значения из многомерного массив, хранящий двойные значения (например, двумерный массив)?
@TheLastStark Как вы думаете, ArrayPrint()
поддерживает двумерные массивы? Из документов непонятно.
это я пробовал, функции MQL5 работают с многомерными массивами
Вы также можете опубликовать его как ответ (по крайней мере, он отвечает на основной вопрос заголовка), так как я не знал об этом. Жаль, что вы не можете получить из него строку (поэтому вы не можете использовать его с файлами, например, хранить значения массива в простом формате), это заставляет вас печатать его.
Я добавил это как ответ, но да, вы правы, это тоже немного грустно видеть, что они наложили это ограничение, мне очень любопытно узнать, почему ограничение действует только на MQL5
Я добавил еще один метод с использованием struct, он тоже не идеален, но все равно попробуйте
Я знаю, что это не идеально, но мы можем использовать ArrayPrint()
для печати массива.
Обратитесь сюда за документацией
void ArrayPrint(
const void& array[], // printed array
uint digits=_Digits, // number of decimal places
const string separator=NULL, // separator of the structure field values
ulong start=0, // first printed element index
ulong count=WHOLE_ARRAY, // number of printed elements
ulong flags=ARRAYPRINT_HEADER|ARRAYPRINT_INDEX|ARRAYPRINT_LIMIT|ARRAYPRINT_ALIGN
);
Вот еще один подход к передаче многомерного массива в функцию, опять же не идеальный, но работает правильно.
//+------------------------------------------------------------------+
//| Struct that is used to hold multi-dimentional array |
//+------------------------------------------------------------------+
template<typename T>
struct MultiDimentionalArray
{
T index2[];
};
//+------------------------------------------------------------------+
//| Array print function that accepts MultiDimentionalArray struct |
//+------------------------------------------------------------------+
string Arr2ToString(MultiDimentionalArray<double> &arr[],string dlm = ",",int digits=2)
{
string res = "";
int i,j;
for(i=0; i<ArraySize(arr); i++)
{
res+ = "[";
for(j=0; j<ArraySize(arr[i].index2); j++)
{
res+=StringFormat("%g%s",NormalizeDouble(arr[i].index2[j],digits),dlm);
}
res = StringSubstr(res,0,StringLen(res) - StringLen(dlm));
res+= "]" + dlm;
}
res=StringSubstr(res,0,StringLen(res)-StringLen(dlm));
return res;
}
Вот пример выполнения
void OnStart()
{
//--- Declaring an array
MultiDimentionalArray<double> arr[];
//--- Adding values to the array
for(int i=0;i<10;i++)
{
//--- Resizing the array - 1st dimention
if (ArraySize(arr)<=i) ArrayResize(arr,ArraySize(arr)+1);
for(int j=0;j<10;j++)
{
//--- Resizing the array - 2nd dimention
if (ArraySize(arr[i].index2)<=j) ArrayResize(arr[i].index2,ArraySize(arr[i].index2)+1);
arr[i].index2[j]=i*j;
}
}
//--- Getting the result as string
string arrResult=Arr2ToString(arr);
//--- Printing the result string
Print(arrResult);
}
Вот результат, который я получил на вкладке экспертов от выполнения приведенного выше кода.
2019.06.11 16:25:47.078 Arrays (EURUSD,H1) [0,0,0,0,0,0,0,0,0,0],[0,1,2,3,4,5,6,7,8,9],[0,2,4,6,8,10,12,14,16,18],[0,3,6,9,12,15,18,21,24,27],[0,4,8,12,16,20,24,28,32,36],[0,5,10,15,20,25,30,35,40,45],[0,6,12,18,24,30,36,42,48,54],[0,7,14,21,28,35,42,49,56,63],[0,8,16,24,32,40,48,56,64,72],[0,9,18
Буду очень признателен, если вы поможете мне с этим вопросом stackoverflow.com/questions/60933737/converting-mql4-ea-to-mql5
Буду признателен за помощь с этим stackoverflow.com/questions/62528297/…
Я создал вознаграждение за вопрос с дополнительной информацией. Пожалуйста, посмотрите stackoverflow.com/questions/62528297/…
Да, мы не можем передать многомерный массив в наши функции, но если вам просто нужно напечатать массив, вы можете использовать функцию
ArrayPrint()
mql5.com/ru/docs/array/arrayprint