Qualsiasi domanda da principiante, per non ingombrare il forum. Professionisti, non passate oltre. Da nessuna parte senza di te - 6. - pagina 125

 
Sepulca:

Io avrei fatto così:


P.S. Risponde allo stesso tempo)))

Non capisco:

if(shift>0) shift=shift-1;

se aperto sulla prima barra, guardando da zero a zero?

 
artmedia70:

Non capisco:

se aperto sulla prima barra, stiamo guardando da zero a zero?


Questa è una piccola rassicurazione nel caso in cui il prezzo di apertura dell'ordine sia già molto più alto di Low al momento dell'apertura. Cioè, non usiamo la barra di apertura per la ricerca. Ecco a cosa serve PERIOD_M1.
 
Sepulca:
Questa è una piccola copertura nel caso in cui il prezzo di apertura dell'ordine sia già significativamente più alto di Low al momento dell'apertura. Cioè non usiamo la barra di apertura per la ricerca. Ecco a cosa serve PERIOD_M1.

Io lo farei in un modo diverso. In generale, inizierei a cercare solo quando la posizione è durata più di una barra. Dopo tutto, il prezzo migliore potrebbe essere proprio sulla barra di apertura, e noi lo sprecheremo.
 
artmedia70:
Io lo farei in modo diverso. In generale, inizierei a cercare solo quando la posizione è durata più di una barra. Dopo tutto, il miglior prezzo potrebbe essere proprio sulla barra di apertura, e noi lo sprecheremo...

Sono d'accordo. Probabilmente sarebbe più efficiente ricordare il prezzo minimo (o massimo) per ogni ordine aperto nell'array ad ogni tick, e chiudere gli ordini quando la condizione viene raggiunta, piuttosto che cercare nuovamente il minimo dal momento in cui l'ordine è stato aperto, per così dire:

 ShortOrderTicket[i]=OrderSend(Symbol(),OP_SELL,......
 if(ShortOrderTicket[i]>=0) min[i]=Bid;
 //.....................................................
 //На каждом тике обновляем минимумы для каждого открытого ордера
 for(i=0;i<N;i++){
  if(ShortOrderTicket[i]>=0){
   min[i]=MathMin(min[i],Ask);
  }
// Если достигнуто условие, закрываем ордер
  if(Ask>min[i]+Delta) if(OrderClose(ShortOrderTicket[i],.....))ShortOrderTicket[i]=-1;
 }
E in caso di problemi come la perdita di connessione, il riavvio del consulente, ecc. dovremmo modificare lo stoploss agli ordini di volta in volta.
 
artmedia70:
Ho sostenuto che l'array deve essere passato qui per riferimento. Altrimenti, la funzione dovrà lavorare con una sola matrice strettamente definita. Anche se l'hai definito globalmente.


Hmm. Dipende da quale array viene passato alla funzione chiamante. Se è un array specifico, allora la funzione chiamata lavorerà con esso... Perché questo è...

Se, per esempio,

void FindOrders(int massive[])
{
   int oType;
   ArrayInitialize(massive, 0);
   for (int i=OrdersTotal() - 1; i>=0; i--)
   {
      if (!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
      if (OrderSymbol() != Symbol()) continue;
      if (OrderMagicNumber() != i_magic) continue;
      
      oType = OrderType();
      massive[oType] = massive[oType] + 1;
   }
}

Chiamandolo in questo modo:

FindOrders(OrdersMassive)

Funziona con l'array OrdersMassive

E così:

FindOrders(massiveOfOrders)

Con l'array massiveOfOrders.

 
Potete dirmi come scoprire lo spread al momento dell'apertura di un trade, o meglio ancora, come farlo visualizzare nel log?
 
Forexman77:
Potete dirmi come trovare la dimensione dello spread, al momento dell'apertura di un trade, o, meglio ancora, come farla visualizzare nel log?

Se (spread) == qualche valore, allora... fate qualcosa... (Per esempio, aprire un ordine o stampare il suo valore nel giornale). O viceversa, se non è uguale o maggiore di (meno di) qualche valore, allora lo visualizziamo nel giornale e facciamo qualcosa. Puoi fare quello che vuoi.
 

Ripeterò la domanda che ho fatto ieri. Non voglio postarlo in un thread separato. Se qualcosa non è chiaro, risponderò a tutte le domande.

Ho ancora difficoltà a chiudere le posizioni richieste. La situazione è la seguente:

1. La chiusura delle posizioni viene monitorata.

2. Non appena l'ultima posizione si è chiusa sulla linea di take... ...tutte le posizioni aperte e in sospeso dovrebbero essere chiuse subito. Tutto è chiuso ordinato per lotti, cioè grandi lotti in una volta sola, e poi più piccoli. Questo è inteso solo per fare esperienza con gli ordini.

L'implementazione è la seguente:

In start() su ogni tick:

 for (int ord=OrdersTotal()-1; ord>=0; ord--)
   {
      if (!OrderSelect(ord,SELECT_BY_POS)) continue;
      if (OrderMagicNumber() != i_magic) continue;
      if (OrderSymbol() != Symbol()) continue;
      if (OrderType() == 6) continue;
        
      g_ticket = OrderTicket();
      g_type = OrderType();
              
      // Блок модификации ордеров       
      if (i_sl != 0 || i_tp != 0)
      {
         if (OrderStopLoss() == 0 && OrderTakeProfit() == 0)
         {
            OrdersModifyer(g_ticket);
         }
      }
      // Закрытие всех ордеров, если последний ордер закрыт
      if (isCloseByTakeLastOpenPos(2))
      {
         // if (g_type < 2)
          {
              ClosePosBySortLots();
          }
          //else
          if (g_type > 1)
          {
              DeletePendingOrders(g_ticket);
          }
      }
   }

Siamo interessati alla chiusura degli ordini a mercato poiché quello in sospeso viene cancellato come richiesto. Ecco cosa abbiamo:

//+-------------------------------------------------------------------------------------+
//| Получаем состояние последней позиции (Открыта или закрыта)                          |
//+-------------------------------------------------------------------------------------+
bool isCloseByTakeLastOpenPos(int delta)
{
   datetime lastOrderCloseTime = -1,               // Время закрытия последнего открытого ордера
            lastOOTHist = -1;                     // Время открытия последнего открытого ордера из истории
   int j = -1;
   pr ("Запустилась функция isCloseByTakeLastOpenPos");
   
   for (int i=OrdersHistoryTotal()-1; i>=0; i--)
   {
      if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) continue;
      if (OrderMagicNumber() != i_magic) continue;
      if (OrderSymbol() != Symbol()) continue;
      if (OrderType() > 1) continue;               // Все удалённые отложки нас не интересуют..
  
      if (lastOrderCloseTime < OrderCloseTime())   // Находим время закрытия..
      {
         lastOrderCloseTime = OrderCloseTime();   // ..последней закрытой позиции в истории
         j = i;
         pr ("j = " + j + "   " + TimeToStr(TimeCurrent()));
      }
   }
  if (OrderSelect(j, SELECT_BY_POS, MODE_HISTORY))
   {
      if (OrderProfit() + OrderCommission() + OrderSwap() <= 0) return (false);
//      pr ("OTP() = " + OrderTakeProfit() + "; OCP() " + OrderClosePrice() + "   " + TimeToStr(TimeCurrent()));
  //    pr ("OOP() = " + OrderOpenPrice() + "; OCP() " + OrderClosePrice() + "   " + TimeToStr(TimeCurrent()));
      if (MathAbs(OrderTakeProfit() - OrderClosePrice()) > delta * pt) return (false);
      else
      {
         lastOOTHist = OrderOpenTime();
         Comment("\n", "FUNC isCloseByTakeLastOpenPos: ",
                 "\n", "j = ", j,
                 "\n", "lastOOTHist = ", TimeToStr(lastOOTHist, TIME_SECONDS));
      }
   }
   else
   {
      Comment("\n", "FUNC isCloseByTakeLastOpenPos: ",
              "\n", "j = ", j,
              "\n", "не удалось выбрать ордер в истории");
      return(false);
   }
  
   for(int h=OrdersTotal()-1; h>=0; h--)
   {
      if (OrderSelect(h, SELECT_BY_POS, MODE_TRADES))
      {
         if (OrderMagicNumber() != i_magic)   continue;
         if (OrderSymbol() != Symbol())       continue;
         if (OrderType() > 1)                 continue;
         if (lastOOTHist < OrderOpenTime()) return(false);  // Выбранная рыночная позиция открыта позже закрытой по тейку
      }
      else {Print("FUNC isCloseByTakeLastOpenPos : не удалось выбрать рыночный ордер");return(false);}
   }
   
   return (true);
}

//+-------------------------------------------------------------------------------------+
//| Закрытие ордеров, отсортированных по размеру лотов                                  |
//+-------------------------------------------------------------------------------------+
void ClosePosBySortLots()
{
   double a[][2];
   int p = 0;
   
   for (int i=OrdersTotal()-1; i>=0; i--)
   {
      if (!OrderSelect(i, SELECT_BY_POS, MODE_TRADES)) continue;
      if (OrderMagicNumber() != i_magic) continue;
      if (OrderSymbol() != Symbol()) continue;
      if (OrderType() < 2)
      {
         p++;
         ArrayResize(a, p);
         a[p-1][0] = OrderLots();
         a[p-1][1] = OrderTicket();
      }
   }
   pr ("ClosePosBySortLots(): " + "p = " + p);
   if (p > 0)
   {
      ArraySort(a, WHOLE_ARRAY, 0, MODE_DESCEND);
      for(i=0; i<p; i++)
      {
         if (OrderSelect(a[i][1], SELECT_BY_TICKET, MODE_TRADES))
         {
             if (OrderCloseTime() == 0) ClosePosBySelect();
         }
      }
   }
}
//+-------------------------------------------------------------------------------------+
//| Закрытие одного, предварительно выбранного ордера                                   |
//+-------------------------------------------------------------------------------------+
void ClosePosBySelect()
{
   bool   fc;
   color  clClose, clCloseBuy = Blue, clCloseSell = Red;
   double ll, pa, pb, pp;
   int    err, it, NumberOfTry = 3;

   if (OrderType() == OP_BUY || OrderType() == OP_SELL)
   {
       for (it=1; it<=NumberOfTry; it++)
       {
           while (!IsTradeAllowed()) Sleep(5000);
           RefreshRates();
           pa = MarketInfo(OrderSymbol(), MODE_ASK);
           pb = MarketInfo(OrderSymbol(), MODE_BID);
           if (OrderType() == OP_BUY)
           {
               pp = pb; clClose = clCloseBuy;
           }
           else
           {
               pp = pa; clClose = clCloseSell;
           }
           ll = OrderLots();
           fc = OrderClose(OrderTicket(), ll, pp, 30, clClose);
           if (fc)
           {
              break;
           }
           else
           {
               err = GetLastError();
           }
       }
   }
   else Print("Некорректная торговая операция. Close ");
}

Per qualche motivo alcuni ordini non vengono chiusi. Stampo alcuni segmenti quando li vedo, non ci capisco niente. Ecco un esempio:

Nel commento si può vedere che lastOOTHist = 01:30:00, anche se questo non è effettivamente corretto. Se controlliamo lastOOTHist nella finestra dei risultati, vedremo che

i loro orari di chiusura sono diversi...

Cosa c'è di sbagliato qui?

 
hoz:


Hmm. Dipende da quale array viene passato alla funzione chiamante. Se è un array specifico, allora la funzione chiamata lavorerà con esso... Perché questo è...

Se, per esempio,

Chiamandolo in questo modo:

Funziona con l'array OrdersMassive

E così:

Con array massiveOfOrders.


Quando si passa una variabile (array) a una funzione per valore, viene creata una variabile locale all'interno della funzione e la si dichiara nell'intestazione: myFunct(int my_var). In questo modo, i cambiamenti di questa variabile non possono essere visti al di fuori della funzione. E nel caso di un array, il compilatore ve lo ricorderà.

Se volete che i cambiamenti nel valore della variabile siano visibili all'esterno (fuori dalla funzione), passate le variabili per riferimento: myFunct(int & my_var)

 
hoz:


Dipende da quale array viene passato alla funzione chiamante. Se c'è una certa matrice, allora la funzione chiamata lavorerà con essa... È così...

Se, per esempio,

Chiamandolo così:

Funziona con l'array OrdersMassive

E da questa parte:

Con array massiveOfOrders

Esattamente. Questo è quello che sto dicendo - perché vorresti che un array specifico sia hard-coded nella funzione stessa, se puoi passarci qualsiasi array della stessa dimensione e tipo.
Motivazione: