Помогите с ООП

 

вот делаю такой класс 

class Strategy1
{
        Strategy1();
 };

class Strategy2
{
        Strategy (string sym);
}

теперь хочу вызвать массив объектов: 

Strategy1 S[10];  // компилируется 
Strategy2 Z("EURUSD")[10]; // не компилируется 

Как тогда быстро создать массив объектов если в конструкторе есть параметры на глобальном уровне? 

Например? создать сначала объекты изменив конструктор, а потом как в OnInit заменить объекты, чтоб они были с символами? 

Может есть решение проще ? 

 

Лично я в подобных случаях использую функцию инициализации у объектов. 

Сперва создается массив, а потом у всех объектов массива вызывается функция Init(), в которой можно задать все параметры. 

Инициализация с помощью отдельной функции допускает повторную инициализацию объектов, а если инициализировать в конструкторе, то повторную инициализацию объекта сделать невозможно. 

 
Georgiy Merts #:

Лично я в подобных случаях использую функцию инициализации у объектов. 

Сперва создается массив, а потом у всех объектов массива вызывается функция Init(), в которой можно задать все параметры. 

Инициализация с помощью отдельной функции допускает повторную инициализацию объектов, а если инициализировать в конструкторе, то повторную инициализацию объекта сделать невозможно. 

ну как то так  я себе и предполагал. Спасибо ! 

 

И еще один момент. Массивы объектов лучше создавать через указатель. Иначе получится массив в стековой памяти, которой очень мало:

Strategy2 *pZ[]; 
if (ArrayResize(pZ, 10) != 10)
{
   Alert("Memory allocation error");
   return;
}

for (int i = 0; i < 10; ++i)
{
   pZ[i] = new Strategy2("EURUSD"); 
   if (CheckPointer(pZ) == POINTER_INVALID)
   {
      Alert("Class instantiation error");
      return;
   }
}
 
Ihor Herasko #:

И еще один момент. Массивы объектов лучше создавать через указатель. Иначе получится массив в стековой памяти, которой очень мало:

Хорошо бы пример проявления потенциальной проблемы.

 
Ihor Herasko #:

И еще один момент. Массивы объектов лучше создавать через указатель. Иначе получится массив в стековой памяти, которой очень мало:

Ой ли.

 
да ерунда конечно
 
fxsaber #:

Хорошо бы пример проявления потенциальной проблемы.

Это не проблема и тем более не потенциальная. Просто особенности работы с памятью в МТ. Вот статический массив:

#define              ARRAY_SIZE           int(60000000)
class Test
{
public:
   int               nA;
   double            fB;
   datetime          dtC;

                     Test(void)
                       : nA(0)
                       , fB(1.0)
                       , dtC(__DATETIME__)
                     {
                     };
};

Test classTest[ARRAY_SIZE];                   // 'classTest' - global variables section is too large
 
void OnStart()
{
}

А вот динамический массив:

#define              ARRAY_SIZE           int(60000000)
class Test
{
public:
   int               nA;
   double            fB;
   datetime          dtC;

                     Test(void)
                       : nA(0)
                       , fB(1.0)
                       , dtC(__DATETIME__)
                     {
                     };
};

Test *pClassTest[];
 
void OnStart()
{
   if (ArrayResize(pClassTest, ARRAY_SIZE) != ARRAY_SIZE)
   {
      Alert("Not enought memory");
      return;
   }
   
   for (int i = 0; i < ARRAY_SIZE; ++i)
   {
      pClassTest[i] = new Test();
      if (CheckPointer(pClassTest[i]) == POINTER_INVALID)
      {
         Alert("Class instantiation error");
         return;
      }
   }

   for (int i = 0; i < ARRAY_SIZE; ++i)
      delete pClassTest[i];
}

В этом случае все компилируется и работает.

 
Ihor Herasko #:

Это не проблема и тем более не потенциальная. Просто особенности работы с памятью в МТ. Вот статический массив:

А вот динамический массив:

В этом случае все компилируется и работает.

А при чем здесь стек? В первом случае Вы попытались статически (на этапе компиляции) выделить большой блок памяти в куче, от чего заслуженно получили от компилятора по лбу, так как в реале совершенно будет не понятно, можно будет выделить столько памяти или нет.

Во втором случае Вы уже в рантайме выделяете большой кусок памяти. И здесь сразу ясно получится выделить или нет, так как программа уже работает с конкретным ресурсом машины (памятью).

И при чем здесь указатели? Массивы в mql двух типов, предопределенные во время стат. компиляции и динамические. Указывать на динамические массивы могут не только указатели *, но и обычные поля класса. Поэтому применение здесь указателей абсолютно не оправдано.

з.ы. странное впечатление от кода, вроде указатели, классы, макросы - при этом полное не понимание происходящего.

 
Ihor Herasko #:

Это не проблема и тем более не потенциальная. Просто особенности работы с памятью в МТ. Вот статический массив:

А вот динамический массив:

В этом случае все компилируется и работает.

Не тот пример, это просто ограничение компилятора, ни о чем не говорящее, просто разработчики так решили. 

Если бы было два варианта - в одном большой статический массив, в другом маленький, и вот, при работе программы, в одном случае возникают проблемы, например, при рекурсивном вызове функции, а в другом при тех же условиях - нет. Вот тогда бы можно было делать вывод...  о вреде свежевыжатого сока)))

 
Vasiliy Sokolov #:

А при чем здесь стек? В первом случае Вы попытались статически (на этапе компиляции) выделить большой блок памяти в куче, от чего заслуженно получили от компилятора по лбу, так как в реале совершенно будет не понятно, можно будет выделить столько памяти или нет.

Во втором случае Вы уже в рантайме выделяете большой кусок памяти. И здесь сразу ясно получится выделить или нет, так как программа уже работает с конкретным ресурсом машины (памятью).

И при чем здесь указатели? Массивы в mql двух типов, предопределенные во время стат. компиляции и динамические. Указывать на динамические массивы могут не только указатели *, но и обычные поля класса. Поэтому применение здесь указателей абсолютно не оправдано.

з.ы. странное впечатление от кода, вроде указатели, классы, макросы - при этом полное не понимание происходящего.

Если чуток изменить пример, сделав объявление на локальном уровне и поставив не такое уж и страшное число, то компилятор уже прямым текстом пишет о том, в чем именно дело:

#property strict
#define              ARRAY_SIZE           int(140000)

class Test
{
   
public:
   int               nA;
   double            fB;
   datetime          dtC;

                     Test(void)
                       : nA(0)
                       , fB(1.0)
                       , dtC(__DATETIME__)
                     {
                     };
};
 
void OnStart()
{
   Test classTest[ARRAY_SIZE];    // the size of local variables is too large
}
Если вдруг захотите поспорить в Ренатом, то велкам.
the size of local variables is too large (more than 512kb)
the size of local variables is too large (more than 512kb)
  • 2014.02.08
  • www.mql5.com
Здравствуйте! Написал индикатор на mql4. Все работало...