1. Наименование торгового инструмента.
Разработчику нужно будет часто менять не все ордера подряд установленные по всем рабочим инструментам, а по определенному, конретному. Поэтому необходимио четко выделять нужный нам торговый инструмент.
2. Тип ордера.
Разработчику необходимо также выбирать из разных видов ордеров вполне определенные. Редко когда нужно менять все подряд ордера даже на одном торговом инструменте.
3. Ордера должны быть четко привязаны к конкретному эксперту или не быть привязанными ни к одному из них, т.к. быть открытыми вручную.
Таким образом, мы всегда должны иметь поле связи в виде MagicNumber, т.е. "магический номер", который разработчик должен всегда присваивать любому эксперту, словно серийный номер конкретного изделия.
Далее, идут спецификации конретного ордера для изменений. Это, собственно, поля, которые нужно изменить в ордере, который мы выбрали в соответствие с первыми тремя пунктами (см. выше). В данном блоке мы не меняем эти поля (значения), мы только передаем их в функцию обработки этого блока.
4. Этими полями обычно являются:
- цена установки ордера (разработчику может понадобиться её изменить);
- цена установки СЛ;
- цена установки ТП;
Если меняется цена установки ордера, то вслед за ней меняется положение как СЛ, так и ТП в подавляющем большинстве случаев (хотя и не всегда).
Назовем функцию для модификации ордера в этом блоке как f_ModOrder(). В соответствие с положениями, описанными выше, данная фукнция будет иметь параметры:
f_ModOrder(string sy, int ot, int mn, double pr, double sl, double tp).
Название параметров, типа, sy, ot, mn ... мы задаем сами и по вашему стилю программирования они могут быть другими. Типы этих параметров очевидны: string, int и т.д.
При разработке функции учтем, что может быть ситуации, один из параметров или два: цена или ТП или СЛ не будет претерпевать изменений. Будем передавать в этом случае в качестве их значений "-1".
Далее представлена сама функция этого блока (1-го из 3) для модификации ордера. Как обычно, нам нужно в цикле пробежаться по всем установленным ордерам на данном торговом счете, вычленить из них необходимый, согласно спецификациям переданных в функцию параметров и далее вызвать функцию 2-го блока, под названием:
f__ModifyOrder().
Саму эту фукнцию мы рассмотрим во 2-м блоке соответственно. Следует обратить внимание, что, получив согласно условиям нужный нам ордер, в фукнцию 2-го блока мы передадим в качестве первого параметра "билет ордера" OrderTicket(), который, собственно мы и искали в данной функции 1-го блока, т.к. "билет ордера" однозначно идентифицирует найденный нами ордер. А вот 2 - 4 параметры передаваемые в функцию 2- го блока и будет соответственно значения цены, СЛ и ТП.
Итак, код самой функции 1-го блока ниже:
- Код: выделить все
void f_ModOrder(string sy, int ot, int mn, double pr, double sl, double tp)
{
/*
13/12/2020
Описание: находит и модифицирует ордер
Используется функция: f__ModifyOrder
Параметры:
sy - наименование инструмента ("0" - текущий символ)
ot - тип ордера
mn - MagicNumber
pr - новая цена установки (-1 - не менять)
sl - новый СЛ ордера (-1 - не менять)
tp - новый ТП ордера (-1 - не менять)
*/
if(sy == "0") sy = Symbol();
for(int i = 0; i < OrdersTotal(); i++)
{
if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if((OrderSymbol() == sy) && (OrderType() == ot))
{
if(OrderMagicNumber() == mn)
{
if(f__ModifyOrder(OrderTicket(), pr, sl, tp))
{
Print(Symbol(), "Modify Trailing ok");
}
else Print(Symbol(), " Modify Trailing fail");
}
}
}
}
}
Возникает вопрос: "Зачем процедуру изменения ордера нужно разбивать на блоки?". Ответ заключен в модульном подходе к программированию. Если какая-то программистская задача может быть разделена на логически независимый блок, она должна быть разделена. Собственно, это азы модульного программирования, на котором возникла теория классов в свое время, но суть её остается и в более универсальных, базовых единицах, таких как функции.