OrderSend() Вопросы - страница 2

 
Yedelkin:
Наверное, пропустил такую тему. Где можно ознакомиться с функцией проверки выставления ордера от KimV?
Она для 4-ки, но глянуть можно, может пригодится. Ознакомиться можно у него на сайте а разделе: "бесплатные библиотеки", библиотека для выставления ордеров.
 
-Alexey-:
Она для 4-ки, но глянуть можно, может пригодится. Ознакомиться можно у него на сайте а разделе: "бесплатные библиотеки", библиотека для выставления ордеров.

от четверки не подойдет. Я для определения позиции использую

PositionSelect

Выбирает открытую позицию для дальнейшей работы с ней. Возвращает true при успешном завершении функции. Возвращает false при неудачном завершении функции. Чтобы получить информацию об ошибке, необходимо вызвать функцию GetLastError().

bool  PositionSelect(
   string  symbol     // имя инструмента
   );

Параметры

symbol

[in]  Наименование финансового инструмента.

Возвращаемое значение

Значение типа bool.

Примечание

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

Функция PositionSelect() копирует данные о позиции в программное окружение, и последующие вызовы PositionGetDouble(), PositionGetInteger() и PositionGetString() возвращают ранее скопированные данные. Это означает, что самой позиции может уже и не быть (или же она изменилась по объему, направлению и т.д.), а данные этой позиции можно еще получать. Для гарантированного получения свежих данных о позиции рекомендуется вызывать функцию PositionSelect() непосредственно перед обращением за ними.

 
sergey1294:

от четверки не подойдет. Я для определения позиции использую PositionSelect

При использовании функции PositionSelect() настораживает то, что она "...возвращает false при неудачном завершении функции". Т.е. значение false возвращается при любом неудачном завершении функции PositionSelect() , а не только при отсутствии позиции.  Иными словами, не исключается ситуация, когда функция OrderSend() вернёт true, функция PositionSelect() вернёт false, а позиция всё-таки откроется.
 
papaklass:
Вы эти ситуации анализируете в предалах одного тика или на разных тиках?

Так-с, исхожу из следующего:

Тик - это изменение цены инструмента. Частота таких изменений непредсказуема: от нескольких в секунду до нескольких в час. Соответственно, работа функций  OrderSend() и PositionSelect()  не должна зависеть от жизнедеятельности тиков. А раз так, то считаю, что контроль за недопущением дублирования ордеров (и анализ соответствующих ситуаций) следует проводить безотносительно к поведению (частоте) тиков.

Поэтому затрудняюсь ответить на вопрос точно :/ 

 
papaklass:

Я, задавая свой вопрос, немножко другое имел ввиду. При приходе очередного тика срабатывает обработчик событий OnTick(). В связи с этим, перефразирую свой вопрос:

Вы эти ситуации анализируете в пределах одного вызова OnTick() или разных? 

Если после прихода нового тика (пользовательского события) возникает необходимость отправки торгового запроса на сервер, то проверка успешности выполнения такого запроса проводится "в пределах обработки" этого самого пришедшего тика (события). Т.е., по Вашей терминологии, "в пределах одного вызова OnTick()" [и независимо от того, сколько тиков (событий) поступило (должно было поступить) во время такой обработки].
 
papaklass:

Ну я так и не могу получить ответ на одном тике Вы выполняете OrderSend()  и PositionSelect()?

Я хочу Вам предложить выполнение этих запросов делать не в пределах одного тика (срабатывания OnTick()), а на двух тиках:

- на первом тике 

т.е. при успешном ответе запроса Вы устанавливаете флаг открытия позиции в buy=true, и прерываете выполнение OnTick() до следующего тика (срабатывания OnTick()) оператор return.

- на втором тике - PositionSelect().

В таком варианте у Вас не будет дублирования открытия позиций. 

 

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

советую перенести контроль исполнения ордеров в OnTrade(), данное событие генерируется только как ответ сервера о совершении торговых операций.

Хотя мне не очень ясно, почему на один ордер приходится 4 события OnTrade() ?

Документация по MQL5: Стандартные константы, перечисления и структуры / Торговые константы / Свойства сделок
Документация по MQL5: Стандартные константы, перечисления и структуры / Торговые константы / Свойства сделок
  • www.mql5.com
Стандартные константы, перечисления и структуры / Торговые константы / Свойства сделок - Документация по MQL5
 
papaklass:

Ну я так и не могу получить ответ на одном тике Вы выполняете OrderSend()  и PositionSelect()? 

По Вашей терминологии получается, что у меня функции OrderSend()  и PositionSelect() выполняются "в пределах одного тика".

papaklass:

...Я хочу Вам предложить выполнение этих запросов делать не в пределах одного тика (срабатывания OnTick()), а на двух тиках:

- на первом тике 

т.е. при успешном ответе запроса Вы устанавливаете флаг открытия позиции в buy=true, и прерываете выполнение OnTick() до следующего тика (срабатывания OnTick()) оператор return.

- на втором тике - PositionSelect().

В таком варианте у Вас не будет дублирования открытия позиций.

 Чуть более ранее предыдущего сообщения я писал, что выполнение функций OrderSend()  и PositionSelect() никак не связано с приходом/неприходом тиков. И кратко объяснил, по какой причине. Поэтому проверка "на втором тике - PositionSelect()" совершенно не должна спасать от дублирования выставления ордеров во всех возможных случаях.

 
Urain:

Хотя мне не очень ясно, почему на один ордер приходится 4 события OnTrade() ?

Об этом была статья про OnTrade().

Urain:

Гарантии что позиция уже будет открыта на следующем тике никакой...

Вот и я примерно о том же.
 
papaklass:

Ну я так и не могу получить ответ на одном тике Вы выполняете OrderSend()  и PositionSelect()?

Я хочу Вам предложить выполнение этих запросов делать не в пределах одного тика (срабатывания OnTick()), а на двух тиках:

- на первом тике 

т.е. при успешном ответе запроса Вы устанавливаете флаг открытия позиции в buy=true, и прерываете выполнение OnTick() до следующего тика (срабатывания OnTick()) оператор return.

- на втором тике - PositionSelect().

В таком варианте у Вас не будет дублирования открытия позиций. 

 

Нет - не в тике. В 1-й секунде.

Вот упростил:

так - если без паузы будет по 2 ордера подряд открывать. Но поставил 3 секунды - и не жалею ))) Все же это открытие ордера.


void OnTimer()
{
  while(true)
  {
     zOrderSend (_Symbol,0.1,ORDER_TYPE_BUY);

     Sleep (1); 

   if (PositionSelect(_Symbol)==true) {break;} 
  }
}
 

Учет ордеров в МТ5 - это целая наука: Обработка торговых событий в эксперте при помощи функции OnTrade() 

Ни какая пауза от повторного открытия не спасет, всегда может возникнуть ситуация, в которой ордер будет исполняться еще на 1 секунду дольше.

 

ps: и не забудьте про мейджик.