![MQL5 - Linguaggio delle strategie di trading integrato nel client terminal MetaTrader 5](https://c.mql5.com/i/registerlandings/logo-2.png)
Ti stai perdendo delle opportunità di trading:
- App di trading gratuite
- Oltre 8.000 segnali per il copy trading
- Notizie economiche per esplorare i mercati finanziari
Registrazione
Accedi
Accetti la politica del sito e le condizioni d’uso
Se non hai un account, registrati
Ciao Cameofx,
Grazie per la gentile risposta.
Questo sistema di codifica è molto semplice e facile.
Tutto fatto manualmente in MetaEditor.
Infatti, il sistema è stato progettato per sviluppare grandi programmi facilmente e con alta velocità.
Il sistema dovrebbe essere anche flessibile e affidabile.
Cordiali saluti!
Ais, grazie per la tua risposta. Ho imparato molto dai tuoi post :)
Cameo
Ciao Amici!
Una cosa del passato mi assilla giorno dopo giorno.
Questa è la documentazione per AIS5 Trade Machine.
Tornerò appena Dio lo deciderà.
Ciao per ora!
Ciao Ais
La tua assenza ci mancherà molto. Abbi cura di te.
Diamo il benvenuto al tuo ritorno.
Il tuo amico, Salute
Ciao Ais
Non riesco a trovare nessuna risposta definitiva nel libro o nel forum. In uno schema logico a relè, una porta AND funzionerebbe come l'esempio precedente. Solo quando ci sono due ingressi 'veri', ci sarà un'uscita 'vera'. Solo allora, il controllo continuerà.Al tuo ritorno, mi dispiace caricarti subito di altre domande. Non è il tuo sistema in particolare, ho questo problema con quasi tutti i programmi. Ha a che fare con le funzioni definite dall'utente. Come fa la funzione definita dall'utente a ottenere la sua definizione.
Per esempio:
Aspettando la vostra risposta. Grazie in anticipo.
Saluti
Ciao Huckleberry
Chiariamo questa parte di codice.
1. Probabilmente le difficoltà maggiori:
1.1. tutti gli umani pensano e agiscono in modo diverso;
1.2. Mi piace usare un numero strettamente limitato di tipi di dati;
1.3. Mi piace usare solo tipi di dati "standard":
1.3.1. "int",
1.3.2. "double",
1.3.3. "string";
1.4. Uso altri tipi di dati solo in casi speciali;
1.5. Denoto il tipo degli elementi del mio programma con una piccola lettera nella prima posizione dei nomi:
1.5.1. "i" per il tipo di dati "int",
1.5.2. "d" per il tipo di dati "double",
1.5.3. "s" per il tipo di dati "string",
1.5.4. "r" per il tipo di dati "undefined";
1.6. questa tecnica di programmazione mi aiuta a controllare il casting dei tipi;
1.7. funzioni e costanti predefinite possono avere anche i seguenti tipi di dati:
1.7.1. "bool",
1.7.2. "color",
1.7.3. "datetime";
1.8. Cerco sempre di fare il casting di questi tipi al tipo "int";
1.9. per oggi il mio casting dei dati di solito è implicito;
1.10. alcuni elementi essenziali delle mie tecniche di programmazione:
1.10.1. Mi piaceva usare la coppia di costanti "TRUE" e "EMPTY" invece della coppia di costanti "TRUE" e "FALSE";
1.10.2. Nelle dichiarazioni "if" a volte ho usato "1" e "0" invece di "TRUE" e "FALSE";
1.10.3. Ho usato la costante "EMPTY" con il valore negativo "-1" per indicare risultati non validi per elementi di dati senza segno;
1.10.4. in futuro userò il tipo "bool" con il prefisso "b" nei nomi.
2. Dobbiamo conoscere i seguenti tipi di dati MQL4:
2.1. "int" è un <!>signed</!> numero intero lungo a 4 byte con valori da -2147483648 a 2147483647;
2.2. "datetime" è un <!>unsigned</!> long 4-byte integer number con valori da 0 a 4294967295;
2.3. assegnando valori "datetime" a variabili "int", otteniamo risultati corretti fino a circa 2038.01.01.
3. Dobbiamo conoscere la funzione "iTime ( symbol, timeframe, shift )" come segue:
3.1. questa funzione restituisce sempre un valore di tipo "datetime";
3.2. ci sono 2 casi diversi di ritorno:
3.2.1. "0" se lo storico locale è vuoto;
3.2.2. tempo aperto per la barra indicato con "shift" in tutti gli altri casi;
3.3. "iTime ( 0, 0, 0 )" restituisce il tempo aperto per la barra zero del grafico corrente;
3.4. se la barra zero è la stessa, "iTime ( 0, 0, 0 )" restituisce lo stesso valore;
3.5. quando la barra zero corrente è completata, questa barra è diventata la barra numero 1 e inizia la formazione della nuova barra zero;
3.6. "iTime ( 0, 0, 0 )" restituisce il nuovo valore;
3.7. quindi, il valore di "iTime ( 0, 0, 0 )" cambia quando cambia la barra zero.
4. Abbiamo evitato di lavorare con la storia vuota nel blocco di programma "2.2.3.1. History data inspection".
5. Quando l'ordine viene chiuso con successo nella funzione "iTryClose" assegniamo "iTradeBarTime = iTime ( 0, 0, 0 ) ;".
6. Nella funzione "iSignalOpen" controlliamo se "iTradeBarTime == iTime ( 0, 0, 0 ) )".
7. Se è vero e il trade ripetuto è vietato da "iTradeBarOnce = 1 ;" allora vietiamo l'apertura del segnale dal valore "EMPTY".
Saluti
Ciao Ais
Grazie per la tua risposta. Studierò su questo e tornerò presto.
Saluti
Ciao Ais,
Scusa per la mia lentezza nella risposta. Ho ricominciato a lavorare nella mia occupazione abituale lunedì. Il tempo è un po' più breve in questi giorni. Il tempo di studio è più breve.
Come avevo accennato prima in questo thread, mi piace rompere le cose fino ai dadi e bulloni. Come fa un pignone a fornire potenza ad un altro e così via. Così ho trovato che il controllo all'interno del programma è affascinante. Vi prego di capire che vi do tutto il rispetto per la pazienza e la conoscenza che avete fornito, ma ho domande sul perché il blocco 2.2.3.1 è necessario.
Come può l'iBaseLag + iBaseBar essere un'espressione?
Ho capito che iBaseLag e iBaseBar sono all'interno del parametro per iHighest e iLowest. A meno che non siano numeri espliciti,
come si può determinare quale numero esatto sarà. iBaseLag è 20, che rappresenta 20 barre utilizzate per calcolare la media.
iBaseBar rappresenta a quale barra dovrebbe iniziare la media. Le barre da 1 a 20, in questo caso, la barra zero non è considerata.
Mi sono preso la libertà di accorciare il programma di /* 2.2.3.1*/. Ho testato il programma e ho trovato gli stessi risultati. Quando si esegue il programma in condizioni reali di trading, questa potrebbe non essere una buona idea.
Qual è la vostra opinione, per favore?
Inoltre, la tua spiegazione al blocco 2.1.2 ha chiarito la mia confusione. iTime restituisce il tempo di apertura della barra zero.
Anche iTradeBarTime è un tipo cast datetime. Il programma sa in quale barra ha avuto luogo lo scambio, quindi solo uno scambio per barra. . iTradeBarOnce == 1
Grazie per l'aiuto
Studierò di più nei prossimi giorni. Ma il blocco reservered 2.1.1 può essere utilizzato per una funzione che fornirebbe posizioni aggiuntive a quelle esistenti. Esempio: un long esistente, poi l'aggiunta di tre o più long?
Con le funzioni che sono già nel programma, ci sarebbero conflitti con le posizioni aggiuntive?
Grazie ancora per tutto. State bene
Saluti
Ciao Huckleberry,
Diamo un'occhiata attenta alla parte principale del programma, incluso il blocco 2.2.3.1.:
////////////////////////////////////////////////////////////////////< 14> // < 2.2.3. Code : Special : Start > //< > int start () // - i 9 l - o //< > { //< > // < 2.2.3.1. History data inspection 4 >`````````````````````````//< > static int iTrigger = 0 ; if ( iTrigger == 0 ) { //< > if ( ( iTime ( 0 , 0 , 0 ) == 0 ) //< > || ( iBars ( 0 , 0 ) < iBaseLag + iBaseBar ) ) //< > return ; else iTrigger = 1 ; } //< > // </2.2.3.1. History data inspection 4 >`````````````````````````//< > // //< > // < 2.2.3.2. Main routine 3 >````````````````````````````````````//< > int iTicket = iGetTicket () ; //< > // //< > if ( iTicket < 0 ) iTryOpen () ; //< > else iTryClose () ; //< > // </2.2.3.2. Main routine 3 >````````````````````````````````````//< > // //< > // < 2.2.3.3. Exception handler 2 >```````````````````````````````//< > int iTrap = GetLastError () ; //< > if ( iTrap > 0 ) Alert ( "Exception " , iTrap ) ; //< > // </2.2.3.3. Exception handler 2 >```````````````````````````````//< > } //< > // </2.2.3. Code : Special : Start > //< > ////////////////////////////////////////////////////////////////////< 0>
1. il blocco 2.2.3.1., il primissimo blocco del programma, è un semplice trigger:
1.1. "static int iTrigger" memorizza il proprio valore per tutta la durata del programma, tale è "static";
1.2. inizialmente "iTrigger == 0";
1.3. l'istruzione "if ( iTrigger == 0 )" viene eseguita ad ogni tick;
1.4. la prima volta, quando "iTrigger == 0", viene eseguita l'ispezione dei dati storici all'interno del blocco {..};
1.5. se i dati storici non sono corretti, viene eseguita l'istruzione "return;";
1.6. significa che l'esecuzione della funzione principale "start ()" è finita;
1.7. al prossimo tick viene eseguita nuovamente l'istruzione "if ( iTrigger == 0 )";
1.8. se i dati storici sono corretti, viene eseguita l'istruzione "iTrigger = 1 ;";
1.9. allora l'esecuzione della funzione principale "start ()" continua;
1.10. al prossimo tick viene eseguita nuovamente l'istruzione "if ( iTrigger == 0 )";
1.11. il valore di "iTrigger" ora e in futuro sarà sempre "== 1" perché è statico;
1.12. quindi in futuro l'ispezione dei dati storici sarà sempre saltata;
1.13. questo è il trigger semplice;
2. l'ispezione dei dati storici consiste di due parti:
2.1. controlla se la storia locale è vuota "iTime ( 0, 0, 0 ) == 0";
2.2. controlla se la dimensione della storia locale è sufficiente per il calcolo di "iATR ( 0, 0, iBaseLag, iBaseBar )", dove:
2.2.1. "iBaseBar" è la barra iniziale per "iATR";
2.2.2. "iBaseLag" è il numero di barre di media per "iATR";
2.2.3. "iBaseLag + iBaseBar" è un'espressione usuale, il risultato è sempre una somma di "iBaseLag" e "iBaseBar";
2.2.4. in altre parole l'espressione "iBaseLag + iBaseBar" è equivalente alla somma di "iBaseLag" e "iBaseBar";
2.2.5. possiamo assegnare qualsiasi valore per "iBaseLag" e "iBaseBar" nell'input del programma nel blocco 1.1.1.;
2.2.6. assegniamo "iBaseLag = 100 ;" e "iBaseBar = 7 ;";
2.2.7. allora il calcolo corretto di "iATR ( 0, 0, iBaseLag, iBaseBar )" sarà possibile, se la dimensione della storia locale è uguale o superiore a 107, perché l'ultimo numero di barra per il calcolo è #106 e la barra numero zero è sempre considerata.
È possibile aggiungere qualsiasi numero di funzioni in qualsiasi programma, il blocco 2.1.1 dimostra solo un esempio di possibile implementazione.
Fornire posizioni aggiuntive richiederà un codice di analisi e gestione delle posizioni molto più complesso della funzione 2.1.4.
Ma tutto è possibile.
Saluti
Ciao Ais
Grazie per la tua rapida risposta. Posso seguire molto di quello che dici. Specialmente riguardo alla funzione iATR. Stai dicendo che l'utilizzo dell'espressione iBaseLag + iBasebar, di per sé, è una parte accettabile della formula. Avevo l'impressione che dovevano essere nei parametri di una funzione definita o non erano ammessi. Questo serve a controllare la dimensione della cronologia locale, se ci sono effettivamente abbastanza barre per procedere. È questo che state indicando? Tanti altri passi, ma passi necessari per raggiungere l'obiettivo. Passi che verrebbero trascurati, o dati per scontati.
Masticare così più sul resto. Grazie per il suo tempo.
Saluti
Ciao Huckleberry
MQL4 è un ambiente molto amichevole, specialmente in confronto, per esempio, al C o agli assemblatori.
I requisiti per vari controlli e altri trucchi sono significativamente ridotti.
Ma l'implementazione dei massimi controlli possibili nell'ambiente di sviluppo riduce sempre le prestazioni.
In ogni modo il programmatore è sempre responsabile del cattivo comportamento del programma.
Quindi per me un controllo ridondante è meglio che, per esempio, una corruzione elementare dei confini.
Saluti