Хочу написать функцию, которая будет определять нужный объем сделки от некоторого процента депозита. Для этого мне нужно знать:
Вот стоимость шага я не могу определить или его считать равным?
Не даром говорят что правильно заданный вопрос это как минимум 2/3 ответа... :)
А теперь приступим к делу.
Шаг №1 - сформулируем нашу задачу, а она такова:
Написать функцию (или набор функций) для расчета размеров лотов от некоторого процента депозита. Насколько я понимаю, под ДЕПОЗИТОМ понимается не баланс, а именно свободные средства...
Шаг №2 - Определяем объем выполняемой работы и остальные вводные:
Насколько я понимаю нам понадобится ДВЕ функции:
1. Рассчитывает размер средств которые могут быть ОТДАНЫ В ЗАЛОГ при открытии новой позиции, расчет ведется по указанному проценту от свободных средств;
2. Возвращает МИНИМАЛЬНЫЙ размер лота для нового ордера или позиции
Что нам понадобится для расчетов:
1. Процент по которому будет рассчитываться оптимальный размер залога;
Хочу написать функцию, которая будет определять нужный объем сделки от некоторого процента депозита. Для этого мне нужно знать...
Продолжим... :)
Шаг №3 - Расчет оптимальной суммы для залога:
Как все мы тут понимаем это должна быть функция возвращающая double, пусть это будет например - double MarginOptimumSize().
Я так думаю что параметрами для нее вполне могут стать: свободных средств, процент и торговое плечо (при этом два последних параметра будут объявлены на прямую, что позволит не указывать их при вызове функции).
Шаблон функции будет выглядеть тогда примерно так:
//Function MarginOptimumSizedoubleMarginOptimumSize(double FreeMargin,doublePercent=10.0,longLeverage=100)
//Функция производит расчет оптимального размера залога для ордера или позиции
{
//----------------------------------------------------------------------------//
//Служебные переменные
doubleResult;//Возвращаемое значение
//----------------------------------------------------------------------------////----------------------------------------------------------------------------//return(Result);
//----------------------------------------------------------------------------//}
Рассчитать оптимальную сумму средств для залога это еще не все что нам надо, нам нужна вторая функция, скажем - doubleLotOptimumSize().
Параметрами для данной функции нам как минимум должны будут служить имя символа и оптимальный залог (возвращаемый функцией MarginOptimumSize())
Для расчета размера лота нам также понадобится и залог для стандартного лота, который лучше рассчитать отдельно, а тут использовать как дополнительный параметр.
Таким образом шаблон данной функции будет выглядеть примерно так:
//Function LotOptimumSizedouble LotOptimumSize(stringWorkSymbol,doubleMarginOptimal=0.0,doubleMarginStd=0.0)
//Функция производит расчет оптимального размера лота для ордеров и позиций
{
//----------------------------------------------------------------------------//
//Служебные переменные
//Минимальный и максимальный размеры лотов, а также шагdouble SymbolLotMin,SymbolLotMax,SymbolLotStep;
double StepSumm,LotStepCount; //Необходимы для расчета лотаdouble LotSize;//Размер лота
double Result;//Возвращаемое значение//----------------------------------------------------------------------------////Защита от дурака!if(MarginOptimal<=0.0)
{
MarginOptimal = MarginOptimumSize(AccountInfoDouble(ACCOUNT_FREEMARGIN));
}
//Получаем вилку по размерам лота
SymbolLotMin = SymbolInfoDouble(WorkSymbol,SYMBOL_VOLUME_MIN); //Минимальный лот
SymbolLotMax = SymbolInfoDouble(WorkSymbol,SYMBOL_VOLUME_MAX); //Максимальный лот
SymbolLotStep = SymbolInfoDouble(WorkSymbol,SYMBOL_VOLUME_STEP); //Шаг лотов
//Расчитываем размер лотаif(MarginOptimal<MarginStd)
//Указанной маржи не достаточно для открытия хотябы одного стандартного лота
//Необходимо получить размер лота который мы можем открыть
{
LotSize = NormalizeDouble(MarginStd/MarginOptimal,2);
}
else//Достоточно маржи для открытия как минимум одного стандартного лота
{
LotSize = NormalizeDouble(MarginOptimal/MarginStd,2);
}
//Оптимизируем размер лота под торговые условия
//Оптимизация. Шаг №1 - Проверка на мин и макс значения размера лотаif(LotSize<SymbolLotMin){LotSize=SymbolLotMin;} //Лот меньше минимальногоif(LotSize>SymbolLotMax){LotSize=SymbolLotMax;} //Лот больше максимального
//Оптимизация. Шаг №2 - Перерасчет размера лота
if(LotSize>SymbolLotMin)
{
StepSumm = LotSize-SymbolLotMin;
LotStepCount = StepSumm/SymbolLotStep-NormalizeDouble(MathMod(StepSumm/SymbolLotStep,1.0),2);
LotSize = SymbolLotMin+LotStepCount*SymbolLotStep;
}
Result = LotSize;
//----------------------------------------------------------------------------//return(Result);
//----------------------------------------------------------------------------//}
Шаг №6 - Расчет суммы залога по стандартному лоту
Вот и остался последний этап, создать последнюю функцию для расчета залога по стандартному лоту.
Не буду долго ее описывать, скажу только, что для расчета залога по EUR проще всего использовать такую формулу:
Подскажите, пожалуйста, как грамотно оформить код, если используемая стратегия требует выставления второго приказа (в примере - OrderSend(BigDogSell,ResultSell)) только после успешного размещения первого отложенного ордераOrderSend(BigDogBuy,ResultBuy). Иными словами, как грамотно подстраховаться от выставления советником второго ордера, если по каким -либо причинам терминал в течение некоторого времени не получает от сервера сигнал об успешном размещении первого отложенного ордера?
Yedelkin: Подскажите, пожалуйста, как грамотно оформить код, если используемая стратегия требует выставления второго приказа (в примере - OrderSend(BigDogSell,ResultSell)) только после успешного размещения первого отложенного ордера OrderSend(BigDogBuy,ResultBuy). Иными словами, как грамотно подстраховаться от выставления советником второго ордера, если по каким -либо причинам терминал в течение некоторого времени не получает от сервера сигнал об успешном размещении первого отложенного ордера?
В 5-ой версии языка MQL появилась масса нововведений, в том числе работа с событиями различных типов (события таймера, торговые события, пользовательские и т.д.). Возможность обработки событий позволяет создавать совершенно новый тип программ для автоматического и полуавтоматического трейдинга. В этой статье мы рассмотрим торговые события и напишем для функции OnTrade() код, который будет обрабатывать событие Trade.
И снова добрый день!)
Хочу написать функцию, которая будет определять нужный объем сделки от некоторого процента депозита. Для этого мне нужно знать:
Вот стоимость шага я не могу определить или его считать равным?
Не даром говорят что правильно заданный вопрос это как минимум 2/3 ответа... :)
А теперь приступим к делу.
Шаг №1 - сформулируем нашу задачу, а она такова:
Написать функцию (или набор функций) для расчета размеров лотов от некоторого процента депозита. Насколько я понимаю, под ДЕПОЗИТОМ понимается не баланс, а именно свободные средства...
Шаг №2 - Определяем объем выполняемой работы и остальные вводные:
Насколько я понимаю нам понадобится ДВЕ функции:
1. Рассчитывает размер средств которые могут быть ОТДАНЫ В ЗАЛОГ при открытии новой позиции, расчет ведется по указанному проценту от свободных средств;
2. Возвращает МИНИМАЛЬНЫЙ размер лота для нового ордера или позиции
Что нам понадобится для расчетов:
1. Процент по которому будет рассчитываться оптимальный размер залога;
2. Размер свободных средств;
3. Размер торгового плеча (скажем, 100 или 500);
4. Минимальный размер лота для данного инструмента;
5. Максимальный размер лота для данного инструмента;
6. Шаг наращивания размера лота
7. Другие данные, которые возможно понадобятся
PS
Тут не учитывается уже существующие позиции и отложники...
Хочу написать функцию, которая будет определять нужный объем сделки от некоторого процента депозита. Для этого мне нужно знать...
Продолжим... :)
Шаг №3 - Расчет оптимальной суммы для залога:
Как все мы тут понимаем это должна быть функция возвращающая double, пусть это будет например - double MarginOptimumSize().
Я так думаю что параметрами для нее вполне могут стать: свободных средств, процент и торговое плечо (при этом два последних параметра будут объявлены на прямую, что позволит не указывать их при вызове функции).
Шаблон функции будет выглядеть тогда примерно так:
Что нам понадобится для расчетов:
1. Процент по которому будет рассчитываться оптимальный размер залога;
2. Размер свободных средств;
3. Размер торгового плеча (скажем, 100 или 500);
4. Минимальный размер лота для данного инструмента;
5. Максимальный размер лота для данного инструмента;
6. Шаг наращивания размера лота
7. Другие данные, которые возможно понадобятся
PS
Тут не учитывается уже существующие позиции и отложники...
1. Это входной параметр;
2. Это AccountInfoDouble(ACCOUNT_FREEMARGIN);
3. Мне пока не ясно для чего нам нужно знать это. Объясните пожалуйста;
4. Это SymbolInfoDouble(Symbol(),SYMBOL_VOLUME_MIN);
5. Это SymbolInfoDouble(Symbol(),SYMBOL_VOLUME_MAX);
6. Это SymbolInfoDouble(Symbol(),SYMBOL_VOLUME_STEP);
Имея шаблон функции прикинем ее начинку.
Шаг №4 - Функция double MarginOptimumSize():
PS
Оптимизация под реальный Leverage для избежания ошибки расчета на торговых счетах где плечо > 100.
Теперь займемся основной функцией.
Шаг №5 - Функция double LotOptimumSize():
Рассчитать оптимальную сумму средств для залога это еще не все что нам надо, нам нужна вторая функция, скажем - double LotOptimumSize().
Параметрами для данной функции нам как минимум должны будут служить имя символа и оптимальный залог (возвращаемый функцией MarginOptimumSize())
Для расчета размера лота нам также понадобится и залог для стандартного лота, который лучше рассчитать отдельно, а тут использовать как дополнительный параметр.
Таким образом шаблон данной функции будет выглядеть примерно так:
Шаг №6 - Расчет суммы залога по стандартному лоту
Вот и остался последний этап, создать последнюю функцию для расчета залога по стандартному лоту.
Не буду долго ее описывать, скажу только, что для расчета залога по EUR проще всего использовать такую формулу:
Залог = Lot*OpenPrice/Leverage;
где:
Lot - размер лота в базовой валюте (для стандартного контракта - SYMBOL_TRADE_CONTRACT_SIZE);
OpenPrice - Текущая цена открытия позиции или ордера
Leverage - Размер предоставленного плеча (ACCOUNT_LEVERAGE)
3. Мне пока не ясно для чего нам нужно знать это. Объясните пожалуйста;
Это объясняется тем что при расчете залога для счетов с разным Leverage необходимо его учитывать.
Для иллюстрации приведу два примера расчета для залога по EUR для счетов различающихся только Leverage (100 и 500)
Вводные
Свободно средств - 25000 $
Процент от депозита - 10%
Минимальный лот - 0.10
Шаг изменения - 0,01
Рассчитываем залог по проценту от свободных средств
2500$ = (25000/100)*10 - верно для счетов где Leverage = 100 (но не верно для счетов с плечом > 100)
500$ = (25000/500)*10 - верно для счетов где Leverage = 500 (но не верно для счетов с плечом < 500)
Расчет залога для стандартного лота
1267.7$ = (100000*1.2677)/100 - верно для счетов где Leverage = 100 (но не верно для счетов с плечом > 100)
253.54$ = (100000*1.2677)/500 - верно для счетов где Leverage = 500 (но не верно для счетов с плечом < 500)
Имея шаблон функции прикинем ее начинку.
Шаг №4 - Функция double MarginOptimumSize()...
Данная функция не совсем подходит для универсального расчета, вот более совершенная (на мой взгляд) функция:
PS
Тут я исправил расчет залога для счетов где Leverage<>100.
Подразумевается, что при плече меньше 100 необходимо средств больше, а при плече больше 100 - меньше...
Данная функция не совсем подходит для универсального расчета, вот более совершенная (на мой взгляд) функция:
PS
Тут я исправил расчет залога для счетов где Leverage<>0.
Подразумевается, что при плече меньше 100 необходимо средств больше, а при плече больше 100 - меньше...
Подскажите, пожалуйста, как грамотно оформить код, если используемая стратегия требует выставления второго приказа (в примере - OrderSend(BigDogSell,ResultSell)) только после успешного размещения первого отложенного ордера OrderSend(BigDogBuy,ResultBuy). Иными словами, как грамотно подстраховаться от выставления советником второго ордера, если по каким -либо причинам терминал в течение некоторого времени не получает от сервера сигнал об успешном размещении первого отложенного ордера?