Вопросы по ООП в MQL5 - страница 21

 
Alexey Navoykov:
Это чисто тестовый класс или реально собираетесь его использовать?   
Если второе, то так делать не стоит.  Статические переменные не переинициализируются при смене символа, насколько я помню.
Да и вообще, иницилизировать константые статики некими внешними значениями, которые не факт что будут доступны на момент инициализации - не лучшая идея.

второе, я все равно под МТ4 пишу, даже для себя - он не работает в тестере на нескольких символах, если что то полезного увижу в МТ4, тогда с помощью MT4Orders перейду на МТ5 - проверенно мои "творчества" без проблем с этой библиотекой работают

первое, хочу посмотреть саму идею правильного ООП - поэтому и тестирую, чтобы увидеть что получится, пока довольно геморойно все идет.... посмотрим, временем располагаю, вот зарядку себе решил сделать ))))


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

#property strict
int    dig = _Digits;
double point = _Point;
double startbalance = AccountBalance();

и работают такие неправильные инициализации много лет из билда в билд, в общем разбаловали разработчики по самое - самое народ ))))




ЗЫ: тут в общем как всегда при использовании ООП - главное задачу правильно разбить на составные элементы и не наследоваться от всего что под рукой, сейчас не знаю куда текстовый вывод ошибок "присунуть" - это нужно везде, в любом классе и в любом месте программы, скорее всего придется создавать базовый класс как  @Vladimir Simakov выше показал свой код

 
Igor Makanu:

пп 1-3 все решаемо, НО.. ОК, вот со статиками помогли, пусть так ибо есть справка, хоть чем то свое решение можно обосновать, теперь код такой:

создал 3 экземпляра Cdeal, получил в логе:

...

пока все работает как и задумано!

Даже если и работает, но так делать ненадёжно.  Поскольку реализация функции вынесена за пределы класса, то затрудняется контроль за порядком расположения полей в самом классе.  Нужно тогда как минимум написать в классе жирный комментарий, что такие-то поля нельзя менять местами )   Но всё ж лучше был ваш первоначальный вариант. Не стоит жертвовать надёжностью ради экономии строчки кода )
 
Alexey Navoykov:
 Но всё ж лучше был ваш первоначальный вариант. Не стоит жертвовать надёжностью ради экономии строчки кода )

какой именно? - тут пол топика в моих вариантах  )))

а так - да, Вы правы на все сто!

ЗЫ:

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


ЗЫЗЫ: возможно еще день поэкспериментирую, и в итоге пример @Vladimir Simakov возьму за основу - там все предельно ясно

 
Igor Makanu:

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

не нравятся мне 2 момента:

1. повторяю вызов SymbolInfoDouble(_Symbol,SYMBOL_VOLUME_STEP) - ибо не оговорен порядок инициализации, т.е. не факт, что у меня будет сначала инициализирована  VolumeSTEP , а лишь затем уже будет вызван  GetDigitsInVolumeStep()

2. хотелось бы избавиться от  использования статического метода static int        GetDigitsInVolumeStep() - насмотрелся видео на ютубе, что в чистом ООП не гоже использовать статические методы, вот борюсь с ветряными мельницами 

ссылки на видео, он одинаковы по сути https://youtu.be/lfdAwl3-X_c и  https://youtu.be/zME4SOCHT0I 


как бы вот эти 2 момента, которые мне не нравятся по другому переписать ?

1. Ничего страшного в двойном вызове этой функции нет.

2. А Вас не смущает, что те кто против использования статических функций не приводят ни малейших аргументов?

Лучше не смотрите видео от кого попало, а читайте книги.

 
Koldun Zloy:

2. А Вас не смущает, что те кто против использования статических функций не приводят ни малейших аргументов?

а Вы первый кто поддержал меня, что видео  не соответствует ничему из практики, я писал в другом топике свое мнение про видео - докладчик даже на вопросы студентов не смог ответить 

 
Igor Makanu:

а Вы первый кто поддержал меня, что видео  не соответствует ничему из практики, я писал в другом топике свое мнение про видео - докладчик даже на вопросы студентов не смог ответить 

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

 
Artyom Trishkin:

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

если видео смотрел, то должен понимать, что цель .... ну в общем ты тоже ничего не понимаешь и не дорос еще - по крайней мере мне так объяснил А100

ЗЫ: чуть позже с интерфейсами немного поэкспериментирую, может некая "сущность-красотища" появится ))))

 

Посмотрел по поводу статиков его видео, всё ради того, чтобы писать так:

new Type0(new Type1(new Type2(...))); 

Ну обёртку написать над статиком разве проблема?

class Stateless_with_state {
        Stateless q;
        Data d;
        call() {q::call(d);}
};

И через шаблоны явно эффективнее. Понравился вопрос из зала https://www.youtube.com/watch?v=75U9eefFYoU#t=33m25s

 
Igor Makanu:

ЗЫ: чуть позже с интерфейсами немного поэкспериментирую, может некая "сущность-красотища" появится ))))

проверил будет ли работать "Паттерн ООП - Паттерны поведения -Стратегия (Strategy) "

interface IStrategy
  {
   void Algorithm();
  };
//+------------------------------------------------------------------+
class Strategy_1 : public IStrategy
  {
public:
                     Strategy_1()   {Print(__FUNCTION__);}
   void              Algorithm()    {Print(__FUNCTION__);}
  };
//+------------------------------------------------------------------+
class Strategy_2 : public IStrategy
  {
public:
                     Strategy_2()   {Print(__FUNCTION__);}
   void              Algorithm()    {Print(__FUNCTION__);}
  };
//+------------------------------------------------------------------+
class Context
  {
private:
   IStrategy         *s;
public:
                     Context(IStrategy &_strategy) {Print(__FUNCTION__); s = GetPointer(_strategy); s.Algorithm();}
                    ~Context() {delete s;}
  };
//+------------------------------------------------------------------+
void OnStart()
  {
   Context c1(new Strategy_1);
   Context c2(new Strategy_2);
  }
//+------------------------------------------------------------------+

2019.08.31 21:04:40.441 tst (EURUSD,H1) Strategy_1::Strategy_1

2019.08.31 21:04:40.442 tst (EURUSD,H1) Context::Context

2019.08.31 21:04:40.442 tst (EURUSD,H1) Strategy_1::Algorithm

2019.08.31 21:04:40.442 tst (EURUSD,H1) Strategy_2::Strategy_2

2019.08.31 21:04:40.442 tst (EURUSD,H1) Context::Context

2019.08.31 21:04:40.442 tst (EURUSD,H1) Strategy_2::Algorithm


по моему работает без проблем

 
Igor Makanu:

проверил будет ли работать "Паттерн ООП - Паттерны поведения -Стратегия (Strategy) "

2019.08.31 21:04:40.441 tst (EURUSD,H1) Strategy_1::Strategy_1

2019.08.31 21:04:40.442 tst (EURUSD,H1) Context::Context

2019.08.31 21:04:40.442 tst (EURUSD,H1) Strategy_1::Algorithm

2019.08.31 21:04:40.442 tst (EURUSD,H1) Strategy_2::Strategy_2

2019.08.31 21:04:40.442 tst (EURUSD,H1) Context::Context

2019.08.31 21:04:40.442 tst (EURUSD,H1) Strategy_2::Algorithm


по моему работает без проблем

Context(IStrategy* _strategy):s(_strategy){Print(__FUNCTION__); s.Algorithm();}

1. Оператор new возвращает указатель, разрабы конечно намудрили с неявными разыменовываниями, поэтому твой вариант и работает, но лучше уж на недокументированные вещи не завязываться.

2. У нас конечно не С++, но очень похоже, поэтому списки инициализации (не знаю насчет эффективности) это кошерно.