초보자의 질문 MQL5 MT5 MetaTrader 5 - 페이지 201

 
barabashkakvn :

전체 코드를 첨부하거나 코드 조각 전에 변수를 초기화하십시오. 예를 들어 다음과 같이 변수에 무엇이 있는지 결코 알 수 없습니다.

모든 코드:

 //+------------------------------------------------------------------+
//|                                                         USSR.mq5 |
//|                        Copyright 2014, MetaQuotes Software Corp. |
//|                                              http://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2014, MetaQuotes Software Corp."
#property link        "http://www.mql5.com"
#property version    "1.00"
#include <Trade\Trade.mqh>


//--- input parameters
// Входные параметры
input int       StopLoss= 15 ;       // Stop Loss
input int       TakeProfit= 30 ;   // Take Profit
input int       ADX_Period= 8 ;     // Период ADX
input int       MA_Period= 8 ;       // Период Moving Average
input int       EA_Magic= 12345 ;   // Magic Number советника
input double    Adx_Min= 22.0 ;     // Минимальное значение ADX
input double    Lot= 0.01 ;         // Количество лотов для торговли
//--- глобальные переменные
ulong tik= 0 ;
int adxHandle; // хэндл индикатора ADX
int maHandle;   // хэндл индикатора Moving Average
double plsDI[],minDI[],adxVal[]; // динамические массивы для хранения численных значений +DI, -DI и ADX для каждого бара
double maVal[]; // динамический массив для хранения значений индикатора Moving Average для каждого бара
double p_close; // переменная для хранения значения close бара
int STP,TKP; // будут использованы для значений Stop Loss и Take Profit
int TrailingStop=TakeProfit;
double Bid;
CTrade trade;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
//Инациализация советника
int OnInit ()
  {
//--- Получить хэндл индикатора ADX
   adxHandle= iADX ( NULL , 0 ,ADX_Period);
//--- Получить хэндл индикатора Moving Average
   maHandle= iMA ( _Symbol , _Period ,MA_Period, 0 , MODE_EMA , PRICE_CLOSE );
//--- Нужно проверить, не были ли возвращены значения Invalid Handle
   if (adxHandle< 0 || maHandle< 0 )
     {
       Alert ( "Ошибка при создании индикаторов - номер ошибки: " , GetLastError (), "!!" );
       return (- 1 );
     }

   STP = StopLoss;
   TKP = TakeProfit;
   if ( _Digits == 5 || _Digits == 3 )
     {
      STP = STP* 10 ;
      TKP = TKP* 10 ;
     }
   return ( 0 );
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
//Выключение советника
void OnDeinit ( const int reason)
  {
   IndicatorRelease (adxHandle);
   IndicatorRelease (maHandle);
  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
//Обработка событий
void OnTick ()
  {
   while (tik== 0 )
     {
       //--- Достаточно ли количество баров для работы
       if ( Bars ( _Symbol , _Period )< 60 ) // общее количество баров на графике меньше 60?
        {
         Alert ( "На графике меньше 60 баров, советник не будет работать!!" );
         return ;
        }

       // Для сохранения значения времени бара мы используем static-переменную Old_Time.
       // При каждом выполнении функции OnTick мы будем сравнивать время текущего бара с сохраненным временем.
       // Если они не равны, это означает, что начал строится новый бар.

       static datetime Old_Time;
       datetime New_Time[ 1 ];
       bool IsNewBar= false ;

       // копируем время текущего бара в элемент New_Time[0]
       int copied= CopyTime ( _Symbol , _Period , 0 , 1 ,New_Time);
       if (copied> 0 ) // ok, успешно скопировано
        {
         if (Old_Time!=New_Time[ 0 ]) // если старое время не равно
           {
            IsNewBar= true ;   // новый бар
             if ( MQL5InfoInteger ( MQL5_DEBUGGING )) Print ( "Новый бар" ,New_Time[ 0 ], "старый бар" ,Old_Time);
            Old_Time=New_Time[ 0 ];   // сохраняем время бара
           }
        }
       else
        {
         Alert ( "Ошибка копирования времени, номер ошибки =" , GetLastError ());
         ResetLastError ();
         return ;
        }

       //--- советник должен проверять условия совершения новой торговой операции только при новом баре
       if (IsNewBar== false )
        {
         return ;
        }

       //--- Имеем ли мы достаточное количество баров на графике для работы
       int Mybars= Bars ( _Symbol , _Period );
       if (Mybars< 60 ) // если общее количество баров меньше 60
        {
         Alert ( "На графике менее 60 баров, советник работать не будет!!" );
         return ;
        }

       //--- Объявляем структуры, которые будут использоваться для торговли
       MqlTick latest_price;       // Будет использоваться для текущих котировок
       MqlTradeRequest mrequest;     // Будет использоваться для отсылки торговых запросов
       MqlTradeResult mresult;       // Будет использоваться для получения результатов выполнения торговых запросов
       MqlRates mrate[];           // Будет содержать цены, объемы и спред для каждого бара
       ZeroMemory (mrequest);
/*
     Установим индексацию в массивах котировок и индикаторов 
     как в таймсериях
*/
       // массив котировок
       ArraySetAsSeries (mrate, true );
       // массив значений индикатора ADX DI+
       ArraySetAsSeries (plsDI, true );
       // массив значений индикатора ADX DI-
       ArraySetAsSeries (minDI, true );
       // массив значений индикатора ADX
       ArraySetAsSeries (adxVal, true );
       // массив значений индикатора MA-8
       ArraySetAsSeries (maVal, true );

       //--- Получить текущее значение котировки в структуру типа MqlTick
       if (! SymbolInfoTick ( _Symbol ,latest_price))
        {
         Alert ( "Ошибка получения последних котировок - ошибка:" , GetLastError (), "!!" );
         return ;
        }

       //--- Получить исторические данные последних 3-х баров
       if ( CopyRates ( _Symbol , _Period , 0 , 3 ,mrate)< 0 )
        {
         Alert ( "Ошибка копирования исторических данных - ошибка:" , GetLastError (), "!!" );
         return ;
        }

       //--- Используя хэндлы индикаторов, копируем новые значения индикаторных буферов в массивы
       if ( CopyBuffer (adxHandle, 0 , 0 , 3 ,adxVal)< 0 || CopyBuffer (adxHandle, 1 , 0 , 3 ,plsDI)< 0
         || CopyBuffer (adxHandle, 2 , 0 , 3 ,minDI)< 0 )
        {
         Alert ( "Ошибка копирования буферов индикатора ADX - номер ошибки:" , GetLastError (), "!!" );
         return ;
        }
       if ( CopyBuffer (maHandle, 0 , 0 , 3 ,maVal)< 0 )
        {
         Alert ( "Ошибка копирования буферов индикатора Moving Average - номер ошибки:" , GetLastError ());
         return ;
        }
       //--- есть ли открытые позиции?
       bool Buy_opened= false ;   // переменные, в которых будет храниться информация 
       bool Sell_opened= false ; // о наличии соответствующих открытых позиций

       if ( PositionSelect ( _Symbol )== true ) // есть открытая позиция
        {
         if ( PositionGetInteger ( POSITION_TYPE )== POSITION_TYPE_BUY )
           {
            Buy_opened= true ;   // это длинная позиция
           }
         else if ( PositionGetInteger ( POSITION_TYPE )== POSITION_TYPE_SELL )
           {
            Sell_opened= true ; // это короткая позиция
           }
        }
       // Скопируем текущую цену закрытия предыдущего бара (это бар 1)
      p_close=mrate[ 1 ].close;   // цена закрытия предыдущего бара
/*
    1. Проверка условий для покупки : MA-8 растет, 
    предыдущая цена закрытия бара больше MA-8, ADX > 22, +DI > -DI
*/
       //--- объявляем переменные типа boolean, они будут использоваться при проверке условий для покупки
       bool Buy_Condition_1=(maVal[ 0 ]>maVal[ 1 ]) && (maVal[ 1 ]>maVal[ 2 ]); // MA-8 растет
       bool Buy_Condition_2 = (p_close > maVal[ 1 ]);         // предыдущая цена закрытия выше скользяшей средней MA-8
       bool Buy_Condition_3 = (adxVal[ 0 ]>Adx_Min);           // текущее значение ADX больше, чем минимальное (22)
       bool Buy_Condition_4 = (plsDI[ 0 ]>minDI[ 0 ]);           // +DI больше, чем -DI

       //--- собираем все вместе
       if (Buy_Condition_1 && Buy_Condition_2)
        {
         if (Buy_Condition_3 && Buy_Condition_4)
           {
             // есть ли в данный момент открытая позиция на покупку?
             if (Sell_opened)
              {
               Alert ( "Уже есть позиция на покупку !!!" );
               return ; // не добавлять к открытой позиции на покупку
              }
            mrequest.action = TRADE_ACTION_DEAL ;                                 // немедленное исполнение
            mrequest.price = NormalizeDouble (latest_price.ask, _Digits );           // последняя цена ask
            mrequest.sl = NormalizeDouble (latest_price.ask + STP* _Point , _Digits ); // Stop Loss
            mrequest.tp = NormalizeDouble (latest_price.ask - TKP* _Point , _Digits ); // Take Profit
            mrequest.symbol= _Symbol ;                                         // символ
            mrequest.volume = Lot;                                             // количество лотов для торговли
            mrequest.magic = EA_Magic;                                         // Magic Number
            mrequest.type= ORDER_TYPE_SELL ;                                     // ордер на покупку
            mrequest.type_filling = ORDER_FILLING_FOK ;                           // тип исполнения ордера - все или ничего
            mrequest.deviation= 100 ;                                           // проскальзывание от текущей цены
             //--- отсылаем ордер
             OrderSend (mrequest,mresult);
             // анализируем код возврата торгового сервера
             if (mresult.retcode== 10009 || mresult.retcode== 10008 ) // запрос выполнен или ордер успешно помещен
              {
               tik=mresult.order;
               Alert ( "Ордер Buy успешно помещен, тикет ордера #:" ,mresult.order, "!!" );
              }
             else
              {
               Alert ( "Запрос на установку ордера Buy не выполнен - код ошибки:" , GetLastError ());
               return ;
              }
           }
        }
/*
    2. Проверка условий для продажи : MA-8 падает, 
    предыдущая цена закрытия бара меньше MA-8, ADX > 22, -DI > +DI
*/
       //--- объявляем переменные типа boolean, они будут использоваться при проверке условий для продажи
       bool Sell_Condition_1 = (maVal[ 0 ]<maVal[ 1 ]) && (maVal[ 1 ]<maVal[ 2 ]);   // MA-8 падает
       bool Sell_Condition_2 = (p_close <maVal[ 1 ]);                         // предыдущая цена закрытия ниже MA-8
       bool Sell_Condition_3 = (adxVal[ 0 ]>Adx_Min);                         // текущее значение ADX value больше заданного (22)
       bool Sell_Condition_4 = (plsDI[ 0 ]<minDI[ 0 ]);                         // -DI больше, чем +DI

       //--- собираем все вместе
       if (Sell_Condition_1 && Sell_Condition_2)
        {
         if (Sell_Condition_3 && Sell_Condition_4)
           {
             // есть ли в данный момент открытая позиция на продажу?
             if (Buy_opened)
              {
               Alert ( "Уже есть позиция на продажу!!!" );
               return ; // не добавлять к открытой позиции на продажу
              }
            mrequest.action= TRADE_ACTION_DEAL ;                                 // немедленное исполнение
            mrequest.price= NormalizeDouble (latest_price.bid, _Digits );           // последняя цена Bid
            mrequest.sl = NormalizeDouble (latest_price.bid - STP* _Point , _Digits ); // Stop Loss
            mrequest.tp = NormalizeDouble (latest_price.bid + TKP* _Point , _Digits ); // Take Profit
            mrequest.symbol= _Symbol ;                                         // символ
            mrequest.volume = Lot;                                             // количество лотов для торговли
            mrequest.magic = EA_Magic;                                         // Magic Number
            mrequest.type= ORDER_TYPE_BUY ;                                     // ордер на продажу
            mrequest.type_filling= ORDER_FILLING_FOK ;                           // тип исполнения ордера - все или ничего
            mrequest.deviation= 100 ;                                           // проскальзывание от текущей цены
             //--- отсылаем ордер
             OrderSend (mrequest,mresult);
             // получаем код ответа торгового сервера
             if (mresult.retcode== 10009 || mresult.retcode== 10008 ) // запрос выполнен или ордер успешно помещен
              {
               tik=mresult.order;
               Alert ( "Ордер Sell успешно помещен, тикет ордера #:" ,mresult.order, "!!" );
              }
             else
              {
               Alert ( "Запрос на установку ордера Sell не выполнен - код ошибки:" , GetLastError ());
               return ;
              }
           }
        }
     }
   if (TrailingStop> 0 )
     {
       if ( OrderSelect (tik)== true )
        {
         if ( ORDER_TYPE_BUY )
         //if(OrderGetInteger(ORDER_TYPE_BUY)==true)
           {
             if (Bid- ORDER_PRICE_OPEN > _Point *(TrailingStop/ 10 ))
              {
               if ( ORDER_SL <Bid- _Point *(TrailingStop/ 10 ))
                 {
                   bool Ans=trade.OrderModify(tik, ORDER_PRICE_OPEN , NormalizeDouble (Bid- _Point *(TrailingStop/ 10 ), 5 ), ORDER_TP , ORDER_TIME_GTC , ORDER_TIME_EXPIRATION );
                   if (Ans== true )
                    {
                     Alert ( "Цена Stop Loss ордера успешно модифицирована." );
                     return ;
                    }
                 }
              }
           }

         else
           {
             if (Bid- ORDER_PRICE_OPEN < _Point *- 1 *(TrailingStop/ 10 ))
              {
               if ( ORDER_SL >Bid- _Point *(TrailingStop/ 10 ))
                 {
                   bool Ans=trade.OrderModify(tik, ORDER_PRICE_OPEN , NormalizeDouble (Bid- _Point *(TrailingStop/ 10 ), 5 ), ORDER_TP , ORDER_TIME_GTC , ORDER_TIME_EXPIRATION );
                   if (Ans== true )
                    {
                     Alert ( "Цена Stop Loss ордера успешно модифицирована." );
                     return ;
                    }
                 }
              }
           }
        }

     }
   return ;
  }

 
StrangerNet :

모든 코드:


 if ( ORDER_TYPE_BUY )...
   ^^^^^^^^^^^^^^
if (Bid- ORDER_PRICE_OPEN ...
      ^^^^^^^^^^^^^^^^
if ( ORDER_SL <Bid ...
   ^^^^^^^^


도대체 무슨 일이 있다는 것입니다?

 
Reshetov :


도대체 무슨 일이 있다는 것입니다?

))))))))

MQL4 코드를 기본으로 사용했습니다.

 void OnStart ()
  {
   int TrailingStop= 50 ;
//--- модифицирует цену Stop Loss ордера на покупку №12345
   if (TrailingStop> 0 )
     {
       OrderSelect ( 12345 ,SELECT_BY_TICKET);
       if (Bid-OrderOpenPrice()> Point *TrailingStop)
        {
         if (OrderStopLoss()<Bid- Point *TrailingStop)
           {
             bool res=OrderModify(OrderTicket(),OrderOpenPrice(), NormalizeDouble (Bid- Point *TrailingStop, Digits ),OrderTakeProfit(), 0 ,Blue);
             if (!res)
               Print ( "Ошибка модификации ордера. Код ошибки=" , GetLastError ());
             else
               Print ( "Цена Stop Loss ордера успешно модифицирована." );
           }
        }
     }
  }

따라서 쓰레기는 지식이 거의없는 결과이며 4에서 5로의 얇은 전환으로 인해 구부러진 핸들을 곧게 펴는 제안을 수락합니다)))

티켓으로 주문을 선택하고 주문 유형(판매 또는 구매)을 선택한 다음 유형을 기반으로 주문의 현재 상태가 조건(값(현재 가격에서 현재 가격에서 주문의 개시 가격)은 1포인트의 가격에 주어진 값을 곱한 것보다 커야 합니다(내 코드에서는 이익 실현 가격을 10으로 나눈 값입니다. 이 조건이 충족되면 중지가 손실 가격은 현재 가격보다 1포인트의 가격에 주어진 값을 곱한 값만큼 낮습니다. 이것이 사실이면 손절매 가격이 변경됩니다.

 
StrangerNet :

그래서 쓰레기는 약간의 지식의 결과이며 결과적으로 4에서 5로 덜 전환됩니다.

참고서 읽기 게으름의 결과로 지적한 것은 주문의 속성 식별자이며 OrderGetDouble , OrderGetInteger 등식별자와 함수를 사용하여 값을 얻습니다.
 
lewvik :
참고서 읽기 게으름의 결과로 지적한 것은 주문의 속성 식별자이며 OrderGetDouble , OrderGetInteger 등식별자와 함수를 사용하여 값을 얻습니다.
또는 작은 예일 수도 있습니다. 저는 구조를 잘 이해하지 못합니다. 아마도 더 정확할 것입니다. if(OrderGetInteger(ORDER_TYPE)==ORDER_TYPE_BUY)?
 
StrangerNet :
또는 작은 예일 수도 있습니다. 저는 구조를 잘 이해하지 못합니다. 아마도 더 정확할 것입니다. if(OrderGetInteger(ORDER_TYPE)==ORDER_TYPE_BUY)?
나는 당신에게 말하지 않을 것입니다 - 나는 상위 5 위 안에 쓰지 않습니다. 하지만 질문을 하겠습니다. 이 검사 결과를 로그에 표시하지 못하게 하는 이유는 무엇입니까?
 
artmedia70 :
나는 당신에게 말하지 않을 것입니다 - 나는 상위 5 위 안에 쓰지 않습니다. 하지만 질문을 하겠습니다. 이 검사 결과를 로그에 표시하지 못하게 하는 이유는 무엇입니까?

일하다)))))))))

 

단점을 수정하면 모든 것이 가이드에 따른 것 같습니다.

 if ( OrderSelect (tik)== true )
        {
         //if(ORDER_TYPE_BUY)
         if ( OrderGetInteger ( ORDER_TYPE )== ORDER_TYPE_BUY )
           {
             if (Bid- OrderGetDouble ( ORDER_PRICE_OPEN )> _Point *(TrailingStop/ 10 ))
              {
               if ( OrderGetDouble ( ORDER_SL )<Bid- _Point *(TrailingStop/ 10 ))
                 {
                   bool Ans=trade.OrderModify(tik, ORDER_PRICE_OPEN , NormalizeDouble (Bid- _Point *(TrailingStop/ 10 ), 5 ), ORDER_TP , ORDER_TIME_GTC , ORDER_TIME_EXPIRATION );
                   if (Ans== true )
                    {
                     Alert ( "Цена Stop Loss ордера успешно модифицирована." );
                     return ;
                    }
                 }
              }
           }

         else
           {
             if (Bid- OrderGetDouble ( ORDER_PRICE_OPEN )< _Point *- 1 *(TrailingStop/ 10 ))
              {
               if ( OrderGetDouble ( ORDER_SL )>Bid- _Point *(TrailingStop/ 10 ))
                 {
                   bool Ans=trade.OrderModify(tik, ORDER_PRICE_OPEN , NormalizeDouble (Bid- _Point *(TrailingStop/ 10 ), 5 ), ORDER_TP , ORDER_TIME_GTC , ORDER_TIME_EXPIRATION );
                   if (Ans== true )
                    {
                     Alert ( "Цена Stop Loss ордера успешно модифицирована." );
                     return ;
                    }
                 }
              }
           }
        }

디버깅에서 조건에 도달합니다.

 if ( OrderSelect (tik)== true )

내부로 들어가지 않고 전체 기능을 통과합니다. 동시에 tik 변수는 전역적으로 선언됩니다. ulong tik=0; - 주문에 대한 응답을 받으면 새 값이 할당됩니다. tik=mresult.order; - 디버깅 시 이 값이 변경됩니다. 왜 조건에 들어가지 않습니까?

 
StrangerNet :
또는 작은 예일 수도 있습니다. 저는 구조를 잘 이해하지 못합니다. 아마도 더 정확할 것입니다. if(OrderGetInteger(ORDER_TYPE)==ORDER_TYPE_BUY)?
 OrderSelect (tiket); //-- выбрать ордер по тикету
if ( OrderGetInteger ( ORDER_TYPE )== ORDER_TYPE_BUY )
{ 

}
 
lewvik :
if( OrderSelect (tik)==true) 함수는 오류 4754를 작성합니다. 주문을 찾을 수 없으며 디버깅 42276230의 tik 값은 생성된 주문 번호 42276230과 같습니다. 무엇이 잘못될 수 있습니까?
사유: