Discussione sull’articolo "Algoritmi Genetici - È Facile!" - pagina 5

 
shurick:

Grazie mille per il chiarimento, la domanda sulla rimozione dei duplicati ha trovato una risposta soddisfacente. Allego il codice dello script che mostra la funzione originale e quella ottimizzata, che dimostra la riduzione del numero di passaggi nei loop. Nel mio commento attuale NON sto segnalando un bug nella funzione, ma suggerendo la sua ottimizzazione; il mio obiettivo principale era quello di scoprire il principio della rimozione dei duplicati, al quale ho ricevuto una risposta esauriente. Ancora una volta, grazie mille per la libreria e per il chiarimento della funzione.

110 e 160 sono troppi per 20 cromosomi.... Hai messo il contatore nel posto sbagliato.

Questo è il posto giusto:

//Selezionare il secondo della coppia....
      for (Ch2=Ch+1;Ch2<PopulChromosCount;Ch2++)
      {
        //count_cicles++; // DEBUG conta quante volte si passano i cicli Ch e Ch2
        if (Ch!=Ch2 && chromosomeUnique[Ch2]!=0)
        {
          count_cicles++; // DEBUG conta quante volte si confrontano i cromosomi.
          //Ripristinare il conteggio del numero di geni identici
          cnt=0;
          //Controlla i geni, purché i geni siano gli stessi.
          for (Ge=1;Ge<=GeneCount;Ge++)
          {
            if (Population[Ge][Ch]!=Population[Ge][Ch2])
              break;
            else
              cnt++;
          }
          //Se il numero di geni identici è uguale al numero totale di geni
          //...il cromosoma viene riconosciuto come un duplicato.
          if (cnt==GeneCount)
            chromosomeUnique[Ch2]=0;
        }

OK. Ora proviamo la stessa popolazione, con gli stessi cromosomi, ma in questa sequenza:

int m_init[20] = {7,7,7,3,9,2,4,5,3,3,5,6,2,4,3,5,10,6,2};

Cosa osserviamo?

 

a Shurick:

Infatti. Il numero di controlli di unicità, con tutti i diversi cromosomi, può essere calcolato con la formula

(PopulChromosCount^2-PopulChromosCount)/2

Nel nostro esempio, che ha 20 cromosomi (supponendo che tutti i cromosomi siano diversi), il numero di controlli sarebbe:

(20*20-20)/2=190

Ciò è confermato da questo controllo:

int  m_init[20]  = {1,2,3,4,5,6,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20};

Se vengono individuati i duplicati, i controlli saranno ancora meno numerosi.

Grazie per la vostra partecipazione attiva al progetto!

Verranno apportate le opportune modifiche alla biblioteca. Anche se le modifiche non influiranno sulle capacità di ricerca dell'algoritmo, renderanno il suo lavoro più razionale.

 
joo:

Cosa stiamo guardando?

Risultato

Anche se le modifiche non incideranno in alcun modo sulle capacità di ricerca dell'algoritmo

Assolutamente giusto, la qualità dell'algoritmo non cambierà, anche se inizialmente ne dubitavo, ma ora me lo avete dimostrato, ma su questi dubbi ha trovato un metodo di ottimizzazione :)

 
Libreria UGA aggiornata ed esempi nell'articolo. Attuale versione gratuita dell'autore 1.2.1.
File:
 
Aggiornamento della libreria UGA e degli esempi per questo articolo. Attuale versione di authoring gratuito 1.2.1.
File:
 

Ho studiato l'articolo e nel codice ho trovato un'incongruenza del genere: in due funzioni per ottenere i valori dell'intervallo viene utilizzata la stessa formula:

//Replicazione
void Replication
...
    //Stabiliamo i confini per la creazione di un nuovo gene
    Minimum = C1-((C2-C1)*ReplicationOffset);
    Maximum = C2+((C2-C1)*ReplicationOffset);
...

/////////////////////////////////////////////

// Mutazione artificiale.
void ArtificialMutation
...
    //Stabiliamo i confini per la creazione di un nuovo gene
    Minimum=C1-((C2-C1)*ReplicationOffset);
    Maximum=C2+((C2-C1)*ReplicationOffset);
...

Cioè si ottengono dati al di fuori dei valori di due geni, il che è caratteristico della "mutazione artificiale". Si tratta di un bug o c'è un'altra spiegazione?

Mi sembra che per il metodo della replicazione sia necessario cambiare i segni:

Minimo = C1+((C2-C1)*ReplicationOffset);

Massimo = C2-((C2-C1)*ReplicationOffset);


 
Batohov:

Ho studiato l'articolo e ho trovato questa incongruenza nel codice: due funzioni utilizzano la stessa formula per ottenere i valori dell'intervallo:

Cioè si ottengono dati al di fuori dei valori di due geni, il che è caratteristico della "mutazione artificiale". Si tratta di un bug o c'è un'altra spiegazione?

Mi sembra che per il metodo della replicazione sia necessario cambiare i segni:

Minimo = C1+((C2-C1)*ReplicationOffset);

Massimo = C2-((C2-C1)*ReplicationOffset);

Non ci sono errori o incoerenze. Sia nella replicazione che nella mutazione artificiale i confini della probabile comparsa di un nuovo gene (le sezioni di codice da lei citate) sono definiti allo stesso modo.

Ma per la replicazione l'area di probabilità si trova all'interno di questi confini, mentre per la mutazione artificiale - al di là di questi confini.

La replicazione serve a trasferire i tratti caratteristici dei geni di entrambi i genitori (entro i confini).

La mutazione artificiale serve a generare nuovi geni diversi da quelli dei genitori (al di fuori dei confini).

 
joo:

Non c'è alcun errore o incoerenza. Sia nella replicazione che nella mutazione artificiale, i confini della probabile comparsa di un nuovo gene (le sezioni di codice da lei citate) sono definiti allo stesso modo.

Ma per la replicazione l'area di probabilità si trova all'interno di questi confini, mentre per la mutazione artificiale - al di là di questi confini.

La replicazione serve a trasferire i tratti caratteristici dei geni di entrambi i genitori (entro i confini).

La mutazione artificiale serve a generare nuovi geni diversi da quelli dei genitori (al di fuori dei confini).

Grazie per la sua rapida risposta, capisco il suo ragionamento.
 
joo:

A proposito, è molto bello essere il distruttore di uno dei più famosi miti dei trader legati a ZZ (il secondo compito nell'articolo). :)

A quanto pare, non ho capito la formulazione del compito. La mia affermazione:

I punti di ingresso per il massimo profitto, con la condizione che il trade minimo sia di N pips, si trovano sui vertici dello ZigZag con la condizione di ginocchio minimo N + Spread pips.

 
joo:

Ho pubblicato alcune interessanti funzioni di prova nel thread del forum MQL4 "Test Multivariable Multiextremal Function", una delle quali è presentata nell'articolo.

Se volete, potete provare a trovare gli estremi delle funzioni proposte utilizzando altri algoritmi di ottimizzazione diversi dal GA e pubblicare qui i risultati. Siete invitati a farlo. Sarà interessante per tutti e in primo luogo per me.

Mi rendo conto che è molto importante valutare la validità dell'adattamento. Uno dei metodi consiste nell'aggiungere rumore ai dati originali.

I codici sorgente dei metodi di ottimizzazione alternativi sono disponibili qui(http://alglib.sources.ru/optimization/) e qui(http://ool.sourceforge.net/).

Ovviamente, ogni algoritmo di ottimizzazione si comporta meglio con le proprie classi di funzioni target.

Quali funzioni target utilizzate nella pratica?