Честный способ увеличения риска ММ советника со стороны ДЦ и возможность борьбы с этим средствами MQL4 - страница 4

 

Ага. Спасибо за коммент и иллюстрацию. Положим в загашничек :)

 
simpleton >>:

В документации описаны 6 типов ордеров, и функция type_name() полностью покрывает всё их множество. Однако, мы видим в логе "OrderType = Unknown type: 6".

Полагаться нельзя, потому что тип ордера 6 недокументирован, - в следующей версии терминала это может работать совсем не так, как в текущей.

В этом случае даже не к чему апеллировать. Поэтому учесть "левые" начисления/списания нельзя.

Допускаю такую вероятность, что ДЦ могут "играть" нумерацией такого рода типов операций.
Поэтому у себя сделал функцию проверки зачисления средств за сегодня:

//+------------------------------------------------------------------+
//|  Возвращает сумму пополнения/снятия средств за сегодня           |
//+------------------------------------------------------------------+
double DepositToDay() {
  int     i, k=OrdersHistoryTotal();
  double  d=0;

  for (i=0; i<k; i++) {
    if (OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) {
      if (OrderType()>5) {
        if (TimeYear (OrderOpenTime())==Year()  &&
            TimeMonth(OrderOpenTime())==Month() &&
            TimeDay  (OrderOpenTime())==Day())
          d=OrderProfit();
        }
      }
    }
  return(d);
}
Ну а дальше, прикручиваем эту функцию в автолот:
//+------------------------------------------------------------------+
//| Внешние переменные советника                                     |
//+------------------------------------------------------------------+
...
extern string  a7                = "MONEY MANAGMENT";
extern double  FixLot            = 10.0;           // фиксированный размер лота
extern bool    AutoLot           = false;          // вкл/выкл режим расчета размера лота в % от депозита
extern double  RiskPercent       = 50.0;           // % депозита для расчета размера лота, используется только при RiskMM = true
                                                   // (размера лота рассчитывается от средств счета)
extern double  MaxLot            = 50.0;           // маскимальный размер лота
//+------------------------------------------------------------------+
//| expert start function                                            |
//+------------------------------------------------------------------+
void start()
   {
   int ticket;
   ...
   ticket = OrderSend(Symbol(), OP_SELL, FixLot(), Bid, 0, Point*150, Point*70, NULL, 0, 0, Red);
   ...
   }
//+------------------------------------------------------------------+
//| Функция расчета размера лота и нормализации к условиям счета     |
//+------------------------------------------------------------------+
double FixLot()
{
  double ret_lot, maxlots, equity;
  int a;
//----
  double mini    = MarketInfo(Symbol(), MODE_MINLOT);
  double maxi    = MarketInfo(Symbol(), MODE_MAXLOT);
  double dolg    = MarketInfo(Symbol(),MODE_MARGINREQUIRED);
  double lotstep = NormalizeDouble(MarketInfo(Symbol(), MODE_LOTSTEP), 2);
  if (lotstep == 0.01) a = 2;
  if (lotstep == 0.1)  a = 1;

    if(!AutoLot)
      { ret_lot = FixLot; maxlots = maxi; }
    if(AutoLot)
      { 
      if(DepositToDay()<=0)   equity = AccountEquity();
      if(DepositToDay()>0)    equity = AccountEquity() - DepositToDay();
        
        ret_lot = NormalizeDouble((equity*RiskPercent/100/dolg), a);
          maxlots = MaxLot; }

         if (ret_lot < mini)      ret_lot = mini;
         if (ret_lot > maxlots)   ret_lot = maxlots;
           ret_lot = NormalizeDouble(ret_lot, a);
  return (ret_lot);
}

Как-то так. Может не совсем правильно, но хоть как-то. Правда есть одно НО.
Такая проверка прокатит, если "ошибочное" зачисление было произведено сегодня.
А если это произошло в 23.59 вчера и сигнал на открытие сделки поступил в 00.00 - уже не прокатит.
Поэтому надо или модифицировать контроль (включая предыдущую дату), или устанавливать запрет на торговлю с 23.30 до 00.30 с дальнейшим изучением историй операций в ручном режиме.
Ессно, всё ИМХО и дальнейшее изучение вопроса до состояния погружения в фобию не предполагаю.
А если вышеизложенное будет кому-то полезно - буду только рад. :)

 
У себя использую внешнюю переменную MaxBalanceForAutoMM.
Если == 0.0, то в расчете лота ничего не меняется. Если задана конкретная сумма, то при достижении баланса счета такой величины, перестает расти лот. Т.е. идет ограничение сверху. Периодически вручную корректирую, - достаточно необременительно получается.
При авто-расчете лота использую минимум из трех величин - баланс, эквити и эта внешняя переменная.