В MQL5 всегда есть место подвигу ! ;) - страница 3

 
mql5:
Кратко.
Функции системных библиотек для x86 (32 бита) процессов имеют специальную обёртку, через которую они переходят в x64, выполняются и возвращаются обратно в x86.

в 64 битной виндовс есть папка SysWOW64. Папка эта предназначена для 32 битных приложений запускаемых в 64 битной ОС, тогда как в папке System32 хранятся обычные 64 битный библиотеки и драйвера.  Если программа запускается как 32 битная, то обращения в папку System32 редиректятся в SysWOW64.

если не кратко, то в МТ5 стал остро вопрос про 32/64 бита.

вопрос очень важный и как раз пришло время его решать.

или папку libraries64 добавить, чтоб терминал сам понимал откуда брать либы
или же дать каким-то образом раскидывать DLL по виндовым папкам System32/SysWow64
или таки дать #ifdef

https://www.mql5.com/ru/forum/6729#comment_199764

ЗЫ.
заявка в СД #381730

 
MetaDriver:

Массив произвольной размерности (для определённости ограничим, скажем, до ^16).

Размерность задаётся при создании количеством параметров, как для обычных массивов. 

XXArray  xx2(5,7),  xx5(12,12,16,16,8);

Должны для всех размерностей работать индексаторы  ( A[i][j][k][n][m]....)

Ну раз сообщество молчит, тогда продолжу ...

Набросок класса N-мерного (double) массива и тест для его проверки.

Размерность описывается (int) массивом в конструкторе.

//+------------------------------------------------------------------+
class CNXdouble
{
        double                 value[];
        int                    size[];
        int                    index;
        int                    ivalue;
public:
                               CNXdouble(const int &n[]);
                              ~CNXdouble()   { ArrayFree(value); ArrayFree(size);}
        double      operator[]   (long x_);
        CNXdouble  *operator[]  (int x_)      { ivalue+=x_*size[index++]; return(GetPointer(this));}
        void         operator=    (double d)    { value[ivalue]=d; index=0; ivalue=0;}
};
//+------------------------------------------------------------------+
CNXdouble::CNXdouble(const int &n[])
{
        int m=1, k=ArraySize(n);
        ArrayResize(size,k);
        size[k-1]=1;
        for(int i=k-2; i>=0; i--) size[i]=n[i+1]*size[i+1];
        for(int i=0; i<k; i++) m*=n[i];
        ArrayResize(value,m);
        index=0;
        ivalue=0;
}
//+------------------------------------------------------------------+
double CNXdouble::operator[] (long x_) 
{
        index=0;
        int i=ivalue;
        ivalue=0;
        return(value[i+(int)x_]);
}
//+------------------------------------------------------------------+
void OnStart()
{
   int n[]={2,3,4,2};      //описание 4-х мерного массива
   int a1=n[0], a2=n[1], a3=n[2], a4=n[3];
   CNXdouble d2(n);
   //запись в массив
   int c=0;
   for(int i=0; i<a1; i++)
       for(int j=0; j<a2; j++) 
           for(int x=0; x<a3; x++) 
               for(int y=0; y<a4; y++)
                   d2[i][j][x][y]=(double)c++;
   //чтение из массива
   string s="";
   for(int i=0; i<a1; i++)
       for(int j=0; j<a2; j++) 
           for(int x=0; x<a3; x++)
               for(long y=0; y<a4; y++)
                   s+=(string)d2[i][j][x][y]+" ";
   Print(s);
}
//+------------------------------------------------------------------+
Файлы:
 

Второй вариант N-мерного (double) массива. Структура массива также задается в конструкторе другим (int) массивом.

Этот вариант немного быстрее предыдущего. И в этом варианте легче создать операции с подмассивами. 

class CNArray
{
        CNArray                    *array[];
        double                      value[];
        bool                        last;
        int                         ivalue;
public:
                                   CNArray(const int &n[]);
                                  ~CNArray();
        double      operator[]      (long x);
        CNArray*   operator[]      (int x);
        void        operator=       (double d) { if(last)value[ivalue]=d;}
};
//+------------------------------------------------------------------+
CNArray::CNArray(const int &n[])
{
        int k=ArraySize(n);
        if(k>1)
        {
                ArrayResize(array,n[0]);
                int n1[];
                ArrayResize(n1,k-1);
                for(int i=0; i<k-1; i++) n1[i]=n[i+1];
                for(int i=0; i<n[0]; i++) array[i]=new CNArray(n1);
                ArrayFree(n1);
                last=false;
        }else if(k==1)
        {
                ArrayResize(value,n[0]);
                last=true;
        }
}
//+------------------------------------------------------------------+
CNArray::~CNArray()
{ 
        if(!last)
        {
                int n=ArraySize(array);
                for(int i=0; i<n; i++) delete array[i];
                ArrayFree(array);
        }else ArrayFree(value);
}
//+------------------------------------------------------------------+
double CNArray::operator[](long x) 
{
        if(last) return(value[(int)x]); else return(0);
}
//+------------------------------------------------------------------+
CNArray* CNArray::operator[](int x)
{ 
        if(last)
        {
                ivalue=x; 
                return(GetPointer(this));
        }else return(array[x]);
}
 
Yurich:

Второй вариант N-мерного (double) массива. Структура массива также задается в конструкторе другим (int) массивом.

Этот вариант немного быстрее предыдущего. И в этом варианте легче создать операции с подмассивами. 

Юрич, ты крут.  Я тут немного отвлёкся от форума на несколько дней, так ты уже пару вариантов нафигачил.

Тэкс.  По первому впечатлению - первый вариант чреват глюками при ошибочном вызове с меньшим числом индексов : т.е. например double x=A[i][j][k]; "трёхмерный вызов" для четырёхмерного массива вернёт double как ни в чём не бывало, но при этом совсем из той позиции массива из которой юзер мечтал.  Причём отследить и обработать такого рода ошибки не видно каким способом.  Зато неоспоримым преимуществом первой реализации является экономность по памяти.  Второй вариант намноого расточительнее.   Зато, как ты верно заметил, в нём можно попробовать достучаться до подмассивов и все трудности на этом путю вполне победимы.

Нужно что-то третье думать.  У меня есть идеи, но доберусь до свободного времени только к ночи ближе, если вообще сегодня доберусь. Но мы тему добьём, обещаю. :)

--

Основная мысля: нужно использовать ещё один класс, что-то вроде "контроллера левых индексов", а крайний правый индекс обрабатывать основным классом (если получится.  если нет, то ещё один класс для правого индекса). При этом базовый массив double (одномерный и единственный) сделать членом основного класса CNArray. Как-то так.

 
MetaDriver

Тэкс.  По первому впечатлению - первый вариант чреват глюками при ошибочном вызове с меньшим числом индексов : т.е. например double x=A[i][j][k]; "трёхмерный вызов" для четырёхмерного массива вернёт double как ни в чём не бывало, но при этом совсем из той позиции массива из которой юзер мечтал.  Причём отследить и обработать такого рода ошибки не видно каким способом. 

покрутил первый способ от Юрича, вроде бы можно ранг массива контролировать так:

class DinArr_Double{
        double                 value[];
        int                    size[];
        int                    index;
        int                    ivalue;
        int                    range;
        bool                   checkerror;
public:
                               DinArr_Double(const int &n[]);
                              ~DinArr_Double()   { ArrayFree(value); ArrayFree(size);}
        double          operator[](long x_);
        DinArr_Double*  operator[](int x_);
        void            operator= (double d)    { value[ivalue]=d; index=0; ivalue=0;}
};
//+------------------------------------------------------------------+
DinArr_Double::DinArr_Double(const int &n[]){
        int m=1, k=ArraySize(n);
        range = ArraySize(n);
        ArrayResize(size,k);
        size[k-1]=1;
        for(int i=k-2; i>=0; i--) size[i]=n[i+1]*size[i+1];
        for(int i=0; i<k; i++) m*=n[i];
        ArrayResize(value,m);
        index=0;
        ivalue=0;
        checkerror = false;
}
//+------------------------------------------------------------------+
double DinArr_Double::operator[](long x_){
        index=0;
        int i=ivalue;
        ivalue=0;
        return(value[i+(int)x_]);
}
//+------------------------------------------------------------------+
DinArr_Double*  DinArr_Double::operator[](int x_){
      ivalue+=x_*size[index++];
      if(index!=range)checkerror = true; else checkerror = false;
      return(GetPointer(this)); } //+------------------------------------------------------------------+ void OnStart(){    int n[]={2,3,4,2};      //описание 4-х мерного массива    int a1=n[0], a2=n[1], a3=n[2], a4=n[3];    DinArr_Double d2(n);    //запись в массив    int c=0;    for(int i=0; i<a1; i++)        for(int j=0; j<a2; j++)            for(int x=0; x<a3; x++)                for(int y=0; y<a4; y++)                    d2[i][j][x][y]=(double)c++;    //чтение из массива    string s="";    for(int i=0; i<a1; i++)        for(int j=0; j<a2; j++)            for(int x=0; x<a3; x++)                for(long y=0; y<a4; y++)                    s+=(string)d2[i][j][x][y]+" ";    Print(s); } //+------------------------------------------------------------------+
 

Задача:

- передать из эксперта в индикатор массив чисел.


Условия.

для передачи данных не использовать
- чартовые события,
- файлы,
- глобальные переменные (они же файлы),
- dll

Документация по MQL5: Основы языка / Переменные / Глобальные переменные
Документация по MQL5: Основы языка / Переменные / Глобальные переменные
  • www.mql5.com
Основы языка / Переменные / Глобальные переменные - Документация по MQL5
 
sergeev:

Задача:

- передать из эксперта в индикатор массив чисел.


Условия.

- не использовать чартовые события, файлы, dll  для передачи данных

Глобальные переменные терминала подойдут?
Документация по MQL5: Основы языка / Переменные / Глобальные переменные
Документация по MQL5: Основы языка / Переменные / Глобальные переменные
  • www.mql5.com
Основы языка / Переменные / Глобальные переменные - Документация по MQL5
 
Тогда остаются поименованные каналы.
 
sandex:
Тогда остаются поименованные каналы.
кто сервер?
 
sergeev:

Задача:

- передать из эксперта в индикатор массив чисел.


Условия.

для передачи данных не использовать
- чартовые события,
- файлы,
- глобальные переменные (они же файлы),
- dll

Ну никого на подвиги не раскрутить :)

Тогда предложу еще один вариант - использовать сабчарт и функции ChartSetString()и ChartGetString().

Причина обращения: