Перейти к содержанию

Исполнение Buy-Sell ордеров, отложек - тема для программистов


Рекомендуемые сообщения

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано



Не смотря в безоговорочную веру в nixxer и 0ll, я бы задержки влепил...
и пусть меня называют параноиком. :)


Тогда уж для верности вставить блок удаления одиночных ордеров с не совпадающими символами, пока две сети не выросли. :)Была у меня такая мысль. Лучшее средство от головной боли - гильотина.
Следуя этой логике надо рассмотреть вариант, когда одна сова будет удалять ордер другой, а другая в это время наоборот. :d
  • Лайк 1
Ссылка на сообщение
Поделиться на другие сайты

  • Ответов 71
  • Создано
  • Последний ответ

Популярные авторы

Популярные авторы

Популярные посты

Дури не хватит одновременно послать ордера с разных советников. Они всяко будут работать по очереди.

Перейти

Хранить данные в комментарии можно но лучше воздерживать или дублировать во внешней БД. Для компрессии строк можно применять base64 кодирование. Если есть подозрения на то что сторонний скрипт или со

Перейти

Длина строки комментариев к ордеру 31 или 33 символа (точно не помню, но точно больше 30). На комментарии никогда не опираюсь когда пишу советники. В основном если нужно записывать информацию, то пишу

Перейти
Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

Есть такой советник, он называется "Мечта ДЦ""

Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано




Не смотря в безоговорочную веру в nixxer и 0ll, я бы задержки влепил...
и пусть меня называют параноиком. :)


Тогда уж для верности вставить блок удаления одиночных ордеров с не совпадающими символами, пока две сети не выросли. :)Была у меня такая мысль. Лучшее средство от головной боли - гильотина.
Следуя этой логике надо рассмотреть вариант, когда одна сова будет удалять ордер другой, а другая в это время наоборот. :d

Не, отрезать пальцы правой на левой руке и наоборот, конечно, удобно до некоторого момента - но вряд ли стоит!...

Как по мне, потупить чуток намного лучше, чем успеть попасть под машину или решительно резать пальцы.
Мы за здравый смысл! :d
Ссылка на сообщение
Поделиться на другие сайты

  • 1 year later...
Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

Уважаемые форумчане и гуру MQL, помогите пожалуйста исправить код функции!!!

Данная функция закрывает все ордера находящиеся в рынке.
Функцию OrderLots () я заменил на функцию FindLastLots(OP_BUY)\FindLastLots(OP_SELL) которая находит ордер последним\наибольшим ЛОТОМ.
В целом преследовал цель одновременного закрытия ордера на ПОКУПКУ и ордера на ПРОДАЖУ с наибольшими лотами (последний открытый ордер на ПОКУПКУ и последний открытый ордер на ПРОДАЖУ)

//=======================================================
void CloseAllLast()
{
for (int i = OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic)
{
if (OrderType() == OP_BUY)
{
if (!OrderClose (OrderTicket(), FindLastLots(OP_BUY), Bid, Slippage))
Print ("не удалось закрыть ордер на покупку!");
}
if (OrderType() == OP_SELL)
{
if (!OrderClose (OrderTicket(), FindLastLots(OP_SELL), Ask, Slippage))
Print ("не удалось закрыть ордер на продажу!");
}
}
}
}

}
//=======================================================

Изменено пользователем Pavel888
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано
evgenforever, так а в чем ошибка то? В функции CloseAllLast() вроде в порядке все, а FindLastLots() Вы не выложили.
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

Ошибка в том, что закрывается только один из ордеров а не парно.

//+------------------------------------------------------------------+
//лот последнего ордера
double FindLastLots (int otype)
{
int oldticket;
double oldlots=0;
ticket = 0;

for (int cnt = OrdersTotal()-1; cnt >= 0; cnt--)
{
if(OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic && OrderType() == otype)
{
oldticket = OrderTicket();
if (oldticket > ticket)
{
ticket = oldticket;
oldlots = OrderLots();
}
}
}
}
return(oldlots);
}
//+------------------------------------------------------------------+

Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано


Ошибка в том, что закрывается только один из ордеров а не парно.



А, понятно. Так Вам сначала нужно найти нужные ордера (их тикеты), а уж затем закрывать их. Например вот так:

//Изменим функцию, которая будет возвращать тикет ордера нужного типа с максимальным объемом 
int FindLastLots (int otype)
{
int ticket=0;
double lot=0;

for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic && OrderType()==otype)
{
if(OrderLots()>lot)
{
ticket=OrderTicket();
lot=OrderLots();
}
}
}
}
return(ticket);
}

//-----------------------------------------------------------------------
//Найдем бай и селл ордера с наибольшим лотом
int buyTicket=FindLastLots (OP_BUY);
int sellTicket=FindLastLots (OP_SELL);

//Закрываем найденные ордера
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if(OrderTicket()==buyTicket || OrderTicket()==sellTicket)
{
double price=Bid;
if(OrderType()==OP_SELL)price=Ask;

if(!OrderClose (OrderTicket(),OrderLots(),price, Slippage))
Print ("не удалось закрыть ордер на покупку!");
}
}
}


Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

Ошибка была в этой строке:
OrderClose (OrderTicket(), FindLastLots(OP_BUY), Bid, Slippage)
нельзя всем подряд тикетам подсовывать для закрытия самый большой лот.
Для поиска тикета самого большого ордера DreamWorks Вам дал решение, единственно я бы не искал ордера в цикле по тикету, а выбрал непосредственно по тикету и закрыл сразу...

  • Лайк 2
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

Уважаемый 0ll, а как это будет выглядеть в коде?

Предложенное решение DreamWorks реализовано с некими правками, все работает.... Огромное спасибо!!!

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

Данная функция считает ПРОФИТ всех ордеров находящихся в рынке. Для корректной работы моего БОТА необходимо считать профит последнего ордера SELL и BUY с наибольшим лотом

double CalculateProfit()
{
double oProfit = 0;
for (int i=OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber()== Magic)
{
if (OrderType() == OP_BUY || OrderType() == OP_SELL)
{
oProfit += OrderProfit();
}

}
}
}
return (oProfit);
}

Изменено пользователем evgenforever
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано
evgenforever, я дал Вам функцию, которая находит необходимые ордера и возвращает их тикеты. Так в чем же проблема, зная нужные тикеты, выбрать эти ордера и подсчитать профит по ним? Хотите в цикле это делайте, точно так же как я предложил Вам закрывать эти ордера, только вместо OrderClose() используйте OrderProfit(). Хотите без цикла сразу выбирайте эти ордера (как 0ll предлагал выше) и складывайте их профиты.
  • Лайк 1
Ссылка на сообщение
Поделиться на другие сайты

  • 2 weeks later...
Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

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


Добавлено: 18-10-2017 18:34:00

Я конечно могу в целом код закинуть, точно описать суть что я хочу реализовать... но меня беспокоят неблагонадежные люди, которые ищут только наживы без капли уважения к авторам.... ХНЫК(


Добавлено: 18-10-2017 19:35:22

В целом мне нужна функция (или функции) которая найдет профит последнего открытого ордера на покупку и на продажу по наибольшему ЛОТУ (или если это один ордер то последний ордер) и закроет ордера одновременно (разнонаправленные между собой) последний ордера с наибольшими лотами (наибольший лот на продажу и наибольший лот на покупку при условии положительного профита.


P.S. А те варианты функции которые были предложены выше закрывают не последние открытые ордера, а первые(((
Изменено пользователем evgenforever
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано
evgenforever чем помочь? у Вас же получилось. Целиком код выкладывать не надо и зря Вы думаете, что "неблагонадёжным" людям он будет интересен - просто в большом коде, написанным по видеоурокам, никто не будет разбираться.
Пишите конкретно проблему и что хотите получить + фрагмент кода.

ПС: давая общие ответы, мы пытаемся стимулировать Вас на работу и рост как программиста. Здесь тема обучения языку, а не бесплатного написания советников.
  • Лайк 1
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

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

Вот что получилось у меня) но она не работает

double CalculateProfitLast()
{
double oProfitLast = 0;
for (int i=OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber()== Magic)
{
lastlotBUY = FindLastLots(OP_BUY);
lastlotSELL = FindLastLots(OP_SELL);
if (((OrderProfit() == lastlotBUY) + (OrderProfit() == lastlotSELL)) >= Profit )
{
oProfitLast += OrderProfit();
}

}
}
}
return (oProfitLast);
}

Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано
evgenforever, вот этот кусок лишен всякого смысла абсолютно:

 if (((OrderProfit() == lastlotBUY) + (OrderProfit() == lastlotSELL)) >= Profit )
{
oProfitLast += OrderProfit();
}

Функция OrderProfit() возвращает сумму профита по выбранному ордеру, а переменные lastlotBUY и lastlotSELL содержат в себе тикеты искомых ордеров. Вы пытаетесь их сравнивать. При этом даже само по себе сравнение делаете не корректно. Оно конечно можно в таком режиме по кусочку просить нас написать то одну функцию, то другую, но поверьте, с теми знаниями программирования, какие есть у Вас сейчас, ничего дееспособного у Вас не получится. У Вас нет четкого понимания того, с чем Вы работаете. Это частая ошибка людей, которые только познакомились с азами MQL и хотят сразу написать рабочего бота по своей стратегии, но все упирается в непонимание то одного, то другого. Это не правильно. Я уже неоднократно повторял, что нужно последовательно идти от простого к сложному. А Вы, посмотрев уроки, хватаетесь за какие-то сложные и непонятные еще для Вас вещи. Мой совет, пишите пока какие-то простенькие скрипты, даже ради баловства и развлекухи. Просто чтобы понять механизмы и устройство MQL. С такими штуками и за советами обращаться проще, не нужно бояться "неблагонадежных людей" и можно все открыто выкладывать ;)
  • Лайк 1
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

Вот такой вариант. Проверку наличия ордеров на Вашей совести. :d

double CalculateProfitLast()
{
static double bLot, bPL, sLot, sPL;
for (int i=OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber()== Magic)
{
if ( OrderType() == OP_BUY && OrderLots() > bLot ) { bLot = OrderLots(); bPL = OrderProfit(); }
if ( OrderType() == OP_SELL && OrderLots() > sLot ) { sLot = OrderLots(); sPL = OrderProfit(); }
}
}
}
return (bPL + sPL);
}

Изменено пользователем 0ll
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

Ценю Ваше желание помочь мне поднять мой уровень владения и понимания MQL4, но поверьте оч тяжело дается...
Данная функция не работает (я так понимаю не хватает проверки наличия ордеров) и не понимаю назначение CONST , что приводит вообще к конфликту функции.

Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

Прости, мой косяк. Не const а static. Все языки давно перемешаны в моей башке <:-p>По поводу наличия ордеров: в общем ничего страшного не будет, функция выдаст некий результат, а Вы должны его правильно интерпретировать.

Изменено пользователем 0ll
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

В итоге что-то не так..

double OPLast = CalculateProfitLast();

if (OPLast >= ProfitLast)
{
CloseAll();
}
///////////////////////////
void CloseAll()
{
for (int i = OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic)
{
if (OrderType() == OP_BUY)
{
if (!OrderClose (OrderTicket(), OrderLots(), Bid, Slippage))
Print ("не удалось закрыть ордер на покупку!");
}
if (OrderType() == OP_SELL)
{
if (!OrderClose (OrderTicket(), OrderLots(), Ask, Slippage))
Print ("не удалось закрыть ордер на продажу!");
}
}
}
}
}

Закрытие ордеров не происходит по причине CalculateProfitLast()


Добавлено: 20-10-2017 20:20:26

И проблема в функции закрытия последних ордеров присутствует..
Закрывается только ордер которые находится в просадке а не парно.

void CloseAllLast()
{
for (int i = OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic)
{
if (OrderType() == OP_BUY)
{
lastlot = FindLastLots(OP_BUY);
if (!OrderClose (OrderTicket(), lastlot, Bid, Slippage))
Print ("не удалось закрыть ордер на покупку!");
}
if (OrderType() == OP_SELL)
{
lastlot = FindLastLots(OP_SELL);
if (!OrderClose (OrderTicket(), lastlot, Ask, Slippage))
Print ("не удалось закрыть ордер на продажу!");
}
}
}
}
}

Изменено пользователем evgenforever
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано
evgenforever судя по коду Вы не понимаете что делаете. Не волнуйтесь - это нормально для начинающего. :d
Вот тот фрагмент кода содержит серьёзную логическую ошибку:
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES)) {
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic) {
if (OrderType() == OP_BUY) {
lastlot = FindLastLots(OP_BUY);
if (!OrderClose (OrderTicket(), lastlot, Bid, Slippage))
...
Вы апускаете цикл по ордерам, открытым на Вашем торговом счёте. В МТ для работы может быть активен только один ордер, го выбирают функцией OrderSelect. После этого все функции для работы с ордерами возвращают параметры именного этого ордера! т.е. например OrderType вернёт тип именно активного ордера, а не какого-то другого. это понятно?
Потом Вы используете функцию FindLastLots, которая запускает свой цикл и делает активными другие ордера.
Затем код возвращается в первый цикл и продолжает работу с последним активным ордером - другим ордером. Именно его Вы и закрываете OrderClose.
ВЫВОД: поиск нужной пары, все проверки и закрытие должны быть в одном цикле! без лишних функций.

Ранее Вы писали что закрыть надо именно последнюю пару, так как её найти? а если из этой пары открылся только один ордер? (ошибка связи была). У Вас есть чёткий алгоритм как идентифицировать пару? или пофиг - закрываем два ордера покрупнее только в разные стороны?
  • Лайк 1
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано (изменено)

Закрывать необходимо пару ордеров (один на продажу и один на покупку) с наибольшими лотами (они будут разные). В любом случае ордер что SELL что BUY имея наибольший лот будут иметь два последних тикета в общем стакане ордеров. И профит необходимо считать именно этих двух ордеров.


Добавлено: 21-10-2017 18:09:20

Было-бы замечательно закрытие этих ордеров сделать через перекрытие этих ордеров чтобы спред компенсировать) Изменено пользователем evgenforever
Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

У Вас всё есть: есть функция поиска последнего лота, только возвращать она должна ТИКЕТ ордера с макс. лотом. В нужный момент запускаете функцию и по найденному тикету закрываете ордера, без всяких циклов.
Всё проще чем кажется.
Давайте проверим код функции, возвращающей тикет ордера с макс.лотом и кусок кода на закрытие ордеров.

Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

//лот последнего ордера
double FindLastLots (int otype)
{
int oldticket;
double oldlots=0;
ticket = 0;

for (int cnt = OrdersTotal()-1; cnt >= 0; cnt--)
{
if(OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic && OrderType() == otype)
{
oldticket = OrderTicket();
if (oldticket > ticket)
{
ticket = oldticket;
oldlots = OrderLots();
}
}
}
}
return(oldlots);
}

А функция закрытия ордера закрывает все ордера:

void CloseAll()
{
for (int i = OrdersTotal() -1; i>=0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic)
{
if (OrderType() == OP_BUY)
{
if (!OrderClose (OrderTicket(), OrderLots(), Bid, Slippage))
Print ("не удалось закрыть ордер на покупку!");
}
if (OrderType() == OP_SELL)
{
if (!OrderClose (OrderTicket(), OrderLots(), Ask, Slippage))
Print ("не удалось закрыть ордер на продажу!");
}
}
}
}
}


Или вот функция которая закрывает ордера на продажу:
if (CountSell() > 0)
{
if ((SLow > 0 || SminiLow > 0) && Stoch_SIGNAL {
for (int i = OrdersTotal() -1; i>= 0; i--)
{
if (OrderSelect (i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderMagicNumber() == Magic && OrderType() == OP_SELL)
if (!OrderClose (OrderTicket(), OrderLots(), Ask, Slippage, Black))
Print ("Ошибка закрытия ордера на покупку!");
}
}
}
}

Ссылка на сообщение
Поделиться на другие сайты

Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

Закрытие всех ордеров пока не нужно.
А вот функцию поиска лота последнего ордера нужно переделать для возврата тикета последнего ордера.
Займитесь этим. там ничего сложного - справитесь.

Ссылка на сообщение
Поделиться на другие сайты

  • 2 weeks later...
Исполнение Buy-Sell ордеров, отложек - тема для програм… Опубликовано

При реализации ТС требующей сопровождения открытых ордеров часто возникает необходимость сохранить дополнительную информацию, например, номер колена, если речи идет о сетке, магик противоположного ордера, или какие нибудь другие необходимые для реализации ТС данные.

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

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

Платформа mt4 предлагает 2 варианта размещения пользовательских данных об ордерах- magic number и комментарий.

В зависимости от ситуации, в magic number можно использовать порядка 3х байт, оставив около 8 бит для идентификации копии эксперта, но этого крайне мало- данные int или float уже не сохранить, поэтому предлагаю обсудить использование комментариев.

Вопросов возникает несколько: во первых допустимая длина комментария (погуглив получил несколько вариантов ответа в диапазоне от 11 до 31 символа), второй момент- якобы ДЦ могут дописывать в комментарии нечто свое, или вовсе их переписывать в некоторых случаях (понять бы еще в каких).

Т.к. ясности не много, прошу ув. разработчиков поделиться опытом.

Ссылка на сообщение
Поделиться на другие сайты

Для публикации сообщений создайте учётную запись или авторизуйтесь

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

Создать учетную запись

Зарегистрируйте новую учётную запись в нашем сообществе. Это очень просто!

Регистрация нового пользователя

Войти

Уже есть аккаунт? Войти в систему.

Войти

  • Специальное предложение


  • Рекомендуемые брокеры

  • ×
    ×
    • Создать...