Ho bisogno di aiuto con l'errore #130 stoploss non valido - pagina 2

 

Il modo migliore per ottenere lo stoploss corretto è quello di pensare correttamente allo spread. Lo spread è la distanza tra l'Ask e il Bid. Quindi, quando si aggiunge uno stoploss a un ordine di acquisto usando Bid - SL include automaticamente lo spread e non sarà necessario codificare per esso e si è in grado di ignorare totalmente lo spread. Per un'operazione di vendita, usare Ask + SL ha lo stesso effetto. Tuttavia, ATTENZIONE --- in tempi di basso volume di trading lo spread diventa più grande e si può finire con uno SL ben lontano dal posto in cui ci si aspetta che sia --- quindi si potrebbe voler aggiungere del codice per prevenire l'aggiunta dello SL oltre una dimensione di spread impostata.

Ora che la questione dello spread è stata risolta, la prossima causa principale dell'errore 130 è che i prezzi sono cambiati mentre il tuo EA sta ancora eseguendo. Questo può essere causato da un EA che impiega molto tempo per l'esecuzione o il server è molto occupato a servire gli scambi che ritardano l'esecuzione dell'EA. Il risultato è che un tick ha fatto iniziare l'esecuzione del tuo EA ma un altro tick è arrivato prima che l'esecuzione sia finita e i prezzi non sono più validi.

In entrambi i casi è necessario aggiornare i prezzi usando RefreshRates: while (RefrshRates() == 1) Sleep(5); ------ o quello che volete come tempo di attesa.

 
BigAl:


In entrambi i casi dovete aggiornare i prezzi usando RefreshRates: while (RefrshRates() == 1) Sleep(5); ------ o qualsiasi cosa vogliate come tempo di attesa.

Questo è corretto solo se il codice usa variabili predefinite https://docs.mql4.com/predefined/variables se il codice usa MarketInfo per Bid e Ask allora RefreshRates non avrà alcuna importanza.
 
qjol:
AFAIK RefreshRates() non ha nulla a che fare con l'errore 130

Punto preso RaptorUK e sono d'accordo che l'uso di MODE_ASK ecc eliminerebbe la necessità di RefreshRates(), ma ho pensato che come nell'esempio di codice di shinobi ....

invio un ordine con per esempio:

int ticket = OrderSend(Symbol(), OP_BUY, position_size, Ask, SLIPPAGE, initial_stop, TAKEPROFIT, NULL, EXPERT_ID, 0, Green);

viene utilizzata la variabile predefinita ASK e quindi il valore ask/bid e lo spread potrebbero essere cambiati dando l'errore 130. In tal caso allora RefreshRates() potrebbe essere usato immediatamente prima di OrderSend

 
BigAl:

Punto preso RaptorUK e sono d'accordo che l'uso di MODE_ASK ecc eliminerebbe la necessità di RefreshRates() ma ho assunto che come nell'esempio di codice di shinobi ....

invio un ordine con per esempio:

int ticket = OrderSend(Symbol(), OP_BUY, position_size, Ask, SLIPPAGE, initial_stop, TAKEPROFIT, NULL, EXPERT_ID, 0, Green);

viene utilizzata la variabile predefinita ASK e quindi il valore ask/bid e lo spread potrebbero essere cambiati dando l'errore 130. In tal caso allora RefreshRates() potrebbe essere usato immediatamente prima di OrderSend

Grazie a tutti per i vostri ottimi consigli!
Sono un po' occupato al momento, ma appena ne avrò la possibilità, proverò tutti i vostri suggerimenti e poi scriverò un post riassuntivo per chiunque possa imbattersi in questo thread con lo stesso problema.

Grazie e stammi bene!

shinobi
 
BigAl: Mando un ordine con per esempio:

int ticket = OrderSend(Symbol(), OP_BUY, position_size, Ask, SLIPPAGE, initial_stop, TAKEPROFIT, NULL, EXPERT_ID, 0, Green);

non dice tutto. Come stai calcolando initial_stop - usando Bid?

Come stai calcolando lo SLIPPAGE - aggiustando per i broker a 4/5 cifre?

 
Ciao ragazzi!

Ho dovuto prendermi una pausa per un po' (trasferimento in una nuova città, nuovo lavoro).
Ma ora vorrei riprendere questo thread e trovare finalmente una soluzione per questo maledetto errore #130 stoploss.

Vi sono grato per tutti i vostri consigli e ho cercato di incorporarli tutti:

1: Spread.
per eliminare lo spread come possibile causa dell'errore, ho impostato lo stoploss come
Bid-stoploss (Long)
Ask+stoploss (Short)

2: Variazione dei tassi di mercato
per eliminare la possibile causa dei tassi di mercato che cambiano prima che l'ordine venga inviato,
ho cambiato il mio codice e sostituito tutte le occorrenze di Ask e Bid con
MarketInfo(Symbol(), MODE_ASK) e MarketInfo(Symbol(), MODE_BID)

3: 4-5 cifre-Broker
per eliminare la possibile causa del numero di cifre non valido, ho arrotondato lo stoploss secondo il codice WHRoeders:
int     pips2points;    // slippage  3 pips    3=points    30=points
double  pips2dbl;       // Stoploss 15 pips    0.0015      0.00150
int     Digits.pips;    // DoubleToStr(dbl/pips2dbl, Digits.pips)

//init digit adjustment
if (Digits % 2 == 1) {      // DE30=1/JPY=3/EURUSD=5 forum.mql4.com/43064#515262
    pips2dbl    = Point*10; pips2points = 10;   Digits.pips = 1;
} else {
    pips2dbl    = Point;    pips2points =  1;   Digits.pips = 0; 
}

OrderSend(Symbol(), OP_BUY, position_size, MarketInfo(Symbol(), MODE_ASK), SLIPPAGE, (MarketInfo(Symbol(), MODE_BID) - stoploss) * pips2dbl, TAKEPROFIT, NULL, EXPERT_ID, 0, Green);
Come detto prima, le variabili SLIPPAGE e TAKEPROFIT nel mio caso sono sempre 0. Quindi anche loro non dovrebbero causare problemi.


Quindi ho incorporato tutti i suggerimenti, ma l'errore persiste ancora. Per quanto posso dire, si verifica con la stessa frequenza di prima, quindi deve esserci un'altra causa.
Ecco un log recente:

tickvalue: 12.50000000
pos size: 37.00000000
Ask/Bid 1262.000000/1261.75000000
stoploss:12.59610000
position_size: 37
Spread 0.25000000

Error could not take long position. L'errore è: #130 invalid stops

La linea di codice OrderSend di cui sopra è stata usata con i valori registrati per provare a prendere una posizione lunga.
Hai altre idee, quale potrebbe essere la causa?

Grazie!
shinobi
 

Questo è un broker ECN?

WHRoeder 2011.09.15 20:36

Sui broker ECN è necessario aprire e poi impostare gli stop.

 
shinobi:
per eliminare la possibile causa del numero di cifre non valido, ho arrotondato lo stoploss secondo il codice di WHRoeders:
  1. Non c'era nessun arrotondamento nel codice che ho postato
  2. Sui broker ECN devi aprire e poi impostare gli stop.
  3. Sui metalli (dove TICKSIZE != Point) il prezzo di apertura per gli ordini pendenti deve essere arrotondato
    double TS=MarketInfo(pair, MODE_TICKSIZE);
    OOP = MathRound(OOP/TS)*TS;
    Non conosco gli stop.

  4. Smettila di dirci quali sono i valori e cosa pensi di aver fatto. Posta il codice.
 

Basta fare

extern double StopLoss = 50;

extern double TakeProfit = 50;

poi per gli acquisti:

double SL=Bid - StopLoss*Point;

double TP=Bid + TakeProfit*Point;

int Ticket=OrderSend(Symbol(),0,1,Ask,2,SL,TP,"",12345);

if( Ticket<0) print("error="GetLastError());

per le vendite:

double SL=Ask + StopLoss*Point;

double TP=Ask - TakeProfit*Point;

int Ticket=OrderSend(Symbol(),1,1,Bid,2,SL,TP,"",12345);

if( Ticket<0) print("error="GetLastError());

poi pubblica il file di log se non funziona.

 
Grazie Raptor, WHRoeder e SDC per le vostre risposte.

SDC:
Ho provato il tuo codice in questo modo:
   int result_ticket = -1;
   double stoploss            = 50;
   double takeprofit          = 50;
   double SL = 0.0;
   double TP = 0.0;
   if(long) {   //take long position
      SL = MarketInfo(Symbol(), MODE_BID) - stoploss * MarketInfo(Symbol(), MODE_POINT));
      TP = MarketInfo(Symbol(), MODE_BID) + takeprofit * MarketInfo(Symbol(), MODE_POINT));
      result_ticket = OrderSend(Symbol(), 0, 1, MarketInfo(Symbol(), MODE_ASK), 2, SL, TP, "", 12345);
   } else {     //take short position
      SL = MarketInfo(Symbol(), MODE_ASK) + stoploss * MarketInfo(Symbol(), MODE_POINT));
      TP = MarketInfo(Symbol(), MODE_ASK) - takeprofit * MarketInfo(Symbol(), MODE_POINT));
      result_ticket = OrderSend(Symbol(), 1, 1, MarketInfo(Symbol(), MODE_BID), 2, SL, TP, "", 12345);
   }

   //check for errors
   if(result_ticket == -1) {
      Log("error="+GetLastError());
      return(-1);
   }
L'unica differenza è che ho sostituito Point, Ask e Bid con MarketInfo per evitare il problema RefreshRates menzionato da Raptor e BigAI.
Il problema persiste con questo semplice esempio. Ottengo ancora

#ESZ1,M5: Posizione di apertura
#ESZ1,M5: tickvalue: 12.50000000
#ESZ1,M5: dimensione pos: 1.00000000
#ESZ1,M5: Ask/Bid 1244.50000000/1244.25000000
#ESZ1,M5: Spread 0.25000000
#ESZ1,M5: SL: 1244.00000000
#ESZ1,M5: TP: 1245.00000000
#ESZ1,M5: errore=130

Raptor:
Attualmente uso UWC-Trader con un conto demo per i test.
Come accennato in precedenza, faccio trading di futures. Per esempio ESZ1 e FDXZ1.

WHRoeder:
Spiacente, nemmeno io arrotondo. Sostituisci "arrotondare" con "regolare per broker a 4/5 cifre". Cioè ho appena applicato il tuo codice.
Ho anche postato l'OrderSend proprio come lo uso nella mia risposta precedente. E i valori di tutte le variabili coinvolte. Non sono sicuro di quale altra parte del codice sarebbe interessante.
Come il mini-esempio, suggerito da SDC, ha mostrato, l'errore può essere scomposto in questo semplice codice. Quindi deve essere più fondamentale.

Non faccio trading di metalli, quindi l'arrotondamento non dovrebbe essere importante.

Proverò la prossima volta:
aprendo (senza stoploss) e poi modificando (impostando lo stoploss) più tardi.

Grazie ancora per i vostri pensieri,

shinobi
Motivazione: