Discussão do artigo "Algoritmos genéticos - é fácil!" - página 4

 
shurick:

Muito obrigado ao autor pela biblioteca!

Adicione a linha "cnt++;" no loop da função de pesquisa pai, caso contrário, ela poderá entrar em um loop eterno!

De fato, em alguns casos, pode haver uma situação em que o loop pode se tornar infinito - quando há apenas um indivíduo na população.

Obrigado pela postagem, farei as alterações em breve.

PS: Provavelmente, esqueci de inserir cnt++, afinal, foi por isso que inseri essa variável. :)

Lembro-me de um desejo de fazer o loop com o operador for(), para que fosse possível regular a "persistência" da busca por pais diferentes, mas depois mudei de ideia, não vendo muito sentido nisso.

Документация по MQL5: Основы языка / Операторы / Оператор цикла for
Документация по MQL5: Основы языка / Операторы / Оператор цикла for
  • www.mql5.com
Основы языка / Операторы / Оператор цикла for - Документация по MQL5
 
@joo É possível usar sua biblioteca para compilar parâmetros dos indicadores Ishimoku, MAKD, etc.?
 
Graff:
@joo É possível usar sua biblioteca para a seleção de parâmetros dos indicadores Ishimoku, MAKD, etc.?

Se você perguntasse: "Para quais tarefas de otimização do trader é impossível usar a biblioteca? - então eu não saberia o que responder.

É claro que você pode.

 
joo:

Se você perguntasse: "Para quais tarefas de otimização do trader é impossível usar a biblioteca?". - então eu não saberia o que responder.

É claro que você pode.

Desculpe-me por uma pergunta boba, mas não sou programador. Se possível, compartilhe o código em que sua biblioteca é usada para combinar vários parâmetros com um indicador (por exemplo, Ishimoku, MAKD) para tornar seu trabalho mais claro.
 
Graff:
Desculpe-me por uma pergunta estúpida, mas não sou programador. Se possível, compartilhe o código em que sua biblioteca é usada para selecionar vários parâmetros para um indicador (por exemplo, Ishimoku, MAKD) para esclarecer seu funcionamento.

A pergunta não é estúpida.

Use o segundo exemplo do artigo. Em vez do indicador ZZ, substitua-o por qualquer outro. No lugar de ler os topos do ZZ, você precisa escrever suas próprias condições (MACD, por exemplo, você obterá o mesmo ziguezague alternativo, mas de acordo com as regras que você definir). Não há nada complicado. Experimente, escreva o código. Se você não conseguir, faça perguntas, demonstrando os pontos problemáticos do código. Aqueles que estiverem interessados verão maneiras de resolver suas tarefas, e você e todos se beneficiarão. Se não quiser aprender a linguagem, entre em contato com o"Work".

 

2joo:

Você poderia me explicar a essência da função RemovalDuplicates()? A pergunta é a seguinte: se tivermos dois cromossomos idênticos, ambos devem ser marcados como duplicatas ou um deles deve permanecer sem ser marcado como duplicata para uso posterior?

Além disso, para acelerar essa função, sugiro que o loop Ch2 comece com o valor Ch+1, já que não faz sentido Ch2 começar do zero:

      //Выбираем второй из пары...

      for (Ch2=Ch+1;Ch2<PopulChromosCount;Ch2++)

e se a resposta à minha pergunta for que ambos os cromossomos estão marcados como duplicados, então, em vez de:

          if(cnt==GeneCount)
            chromosomeUnique[Ch2]=0;

do:

          if (cnt==GeneCount) {
            chromosomeUnique[Ch]=0;
            chromosomeUnique[Ch2]=0;
          }

E se a resposta for que um cromossomo deve ser deixado NÃO marcado como duplicado, então o loop Ch2 deve começar com o valor Ch+1 de qualquer forma.

 
shurick:

2joo:

Você poderia me explicar a essência da função RemovalDuplicates()? A pergunta é: se tivermos dois cromossomos idênticos, ambos devem ser marcados como duplicatas ou um deles deve permanecer sem ser marcado como duplicata para uso posterior?

O algoritmo para essa função é o seguinte:

Marcamos todos os cromossomos com o recurso de exclusividade "1". Acreditamos que todos os cromossomos são únicos.

Verificar se há cromossomos idênticos. Para fazer isso, duplicamos virtualmente a população e comparamos todos os cromossomos entre si, ignorando os pares com o mesmo número de sequência. As duplicatas encontradas são marcadas com o recurso de duplicata "0".

Em seguida, copiamos todos os cromossomos restantes não marcados como "0" para a matriz temporária. Obtemos uma matriz temporária preenchida, sem lacunas, e já sabemos quantos cromossomos exclusivos restam na população.

Em seguida, a única coisa que resta a fazer é copiar os cromossomos de volta para a população. Como você pode ver, não há exclusão de cromossomos, os cromossomos exclusivos são apenas deslocados para o início da população.


Para testar essa função, escreva um script e tente alimentar manualmente combinações complicadas de matrizes preenchidas. Você verá como a função funciona de forma eficiente/ineficiente. Calcule o menor número possível de verificações de colunas na matriz e compare-o com o número de vezes que a função RemovalDuplicates() verifica as colunas.

 
joo:

ZY Para testar essa função, escreva um script e tente alimentar manualmente combinações complicadas de matrizes preenchidas. Você verá como a função é eficaz ou ineficaz. Calcule o menor número possível de verificações de colunas na matriz e compare-o com o número de vezes que a função RemovalDuplicates() verifica as colunas.

Quando você iniciar o loop "for (Ch2=Ch+1)", o número de iterações necessárias e suficientes diminuirá por um fator de 2 e meio e uma das duplicatas não será marcada como duplicata. Aqui eu estava me perguntando o quanto seria mais correto deixar um cromossomo das duplicatas único! Ou seja, a tarefa da função é remover cromossomos idênticos, mas uma cópia dos cromossomos duplicados me parece melhor retornar à população, porque a presença de suas duplicatas não prova sua vitalidade. Por exemplo: se houver uma matriz de cromossomos {1,3,4,7,7,7,7,6,7,8,8}, acho que a remoção ideal de duplicatas seria este resultado: {1,3,4,7,6,8}. Portanto, os cromossomos 7 e 8 serão considerados posteriormente.
 
shurick:
No início do loop "for (Ch2=Ch+1)", o número de iterações necessárias e suficientes será reduzido duas vezes e um dos cromossomos duplicados não será marcado como duplicado. Aqui eu estava me perguntando o quanto seria mais correto deixar um cromossomo das duplicatas único! Ou seja, a tarefa da função é remover cromossomos idênticos, mas uma cópia dos cromossomos duplicados me parece melhor retornar à população, porque a presença de suas duplicatas não prova sua vitalidade. Por exemplo: se houver uma matriz de cromossomos {1,3,4,7,7,7,7,6,7,8,8}, acho que a remoção ideal de duplicatas seria este resultado: {1,3,4,7,6,8}. Portanto, os cromossomos 7 e 8 serão considerados posteriormente.

Sua observação anterior sobre o cnt++ foi justa. Mas desta vez você está errado. Sugiro que você não especule sobre "O que acontecerá se...?", mas escreva um script, teste a função e demonstre o resultado.

Um único cromossomo exclusivo permanece, o restante de suas cópias exatas será reconhecido como duplicatas e "excluído".

Provavelmente, essa é uma das funções mais "quebra-cabeça" de todo o algoritmo UGA. Foi a que me tomou mais tempo. Mas não há erros nela.


PS: O principal é que não deve haver verificações repetidas dos mesmos cromossomos - isso é feito.

O número de verificações de exclusividade é o mínimo necessário. Se estiver falando sobre o número de execuções no operador for(), você pode reduzi-las (enquanto o número de verificações de exclusividade permanecerá o mesmo - o mínimo possível) introduzindo uma variável adicional, cada vez aumentando em um na variável aninhada. Isso tornará a função mais lenta.

PPS Se você enfatizar:

shurick:

....

quão mais correto seria deixar um cromossomo das duplicatas único! Ou seja, a tarefa da função é remover cromossomos idênticos, mas uma cópia de cromossomos duplicados me parece melhor retornar à população, porque a presença de suas duplicatas não prova sua vitalidade.

O trabalho da função é remover as duplicatas. É assim que ela é chamada. Não se trata de remover cromossomos idênticos. Está vendo a diferença? Essa função não faz distinção entre os cromossomos com base em sua viabilidade. Como resultado, apenas os cromossomos únicos permanecem, sem duplicatas.

PPPS Vou fazer mais um esclarecimento, só para garantir.

Suponha que tenhamos uma população composta por 20 cromossomos (para simplificar e esclarecer, com um único gene inteiro), o problema de maximização:

|7|2|3|9|2|4|5|3|3|5|6|2|4|3|5|10|6|7|7|2|

Ou seja, em uma população de cromossomos contendo o gene

2 - 4 peças

3 - 4 peças

4 - 2 peças

5 - 3 peças

6 - 2 peças

7 - 3 peças

9 - 1 peça

10 - 1 peça.

Total - 20 pedaços de cromossomos.

Depois de remover as duplicatas, a população terá a seguinte aparência, com 8 cromossomos restantes:

|7|2|3|9|4|5|6|10|

Portanto, resta um cromossomo único, os demais são duplicados e serão "excluídos"

após a chamada da função.

PopulationRanking();

no final da função.

RemovalDuplicates()

A população terá a seguinte aparência:

|10|9|7|6|5|4|3|2|

 
joo:

PPPS Vou fazer outro esclarecimento, por precaução.

Muito obrigado pelo esclarecimento, a pergunta sobre a remoção de duplicatas está totalmente respondida para minha satisfação. Estou anexando o código do script que demonstra a função original e a otimizada, que demonstra a redução do número de passagens em loops. No meu comentário atual, NÃO estou apontando um erro na função, mas sugerindo sua otimização, e meu objetivo principal era descobrir o princípio da remoção de duplicatas, para o qual recebi uma resposta abrangente. Muito obrigado novamente pela biblioteca e pelas explicações sobre a função.

Resultado do script de verificação de otimização de função

Arquivos anexados: