Campeonato de Otimização de Algoritmos. - página 52

 

Por que importar no segundo exemplo?

//+------------------------------------------------------------------+
// тестовая фитнес функция чемпионата, не известна участникам
#import "\\Projects\\OAC\\lib\\ff.ex5"
// запросить количество параметров ФФ 
int    GetParamCountFF (); 
// запуск ФФ, получеие значения соответствующее параметроам ФФ
double FF (double &array []); 
// произведённое количество запусков ФФ
int    GetCountRunsFF (); 
#import
 
Dmitry Fedoseev:

Bem, eu também poderia escrever isso - o que há de tão pouco claro sobre minha pergunta?

Foi mais uma pergunta retórica, porque tenho certeza de que você a entendeu.

Dmitry Fedoseev:
Por que eu preciso fazer uma pergunta 10 vezes?

É uma pergunta difícil, muitas vezes eu me pergunto a mesma coisa).

DmitryFedoseev:

Por que você precisa de importação no segundo exemplo?

A fim de controlar o algoritmo a partir do script, quantas vezes o algoritmo realmente chamou o FF.

Para a primeira variante ela é claramente visível, porque o script em si faz chamadas, mas para a segunda variante ela não é visível, e é por isso que precisamos da capacidade de acessar a biblioteca FF a partir do script.

 

Agora, quero apelar para todos os participantes, que se consideram "recém-chegados" neste assunto e não esperam seriamente ganhar.

Se abandonarmos toda a "teoria" insana sobre múltiplas dimensões do espaço, que tanto confunde o problema, e nos voltarmos para a matemática pura, vemos que a FF é uma equação.

Esta equação torna-se uma função analítica somente se aplicada a um gráfico.

Mas há uma pergunta - DEVERIA SER? Um gráfico simplesmente ajuda a visualizar a relação entre os parâmetros da equação.

Após 158 páginas de discussão, já podemos formular a essência do problema:

Precisamos encontrar os valores das variáveis do lado direito daequação em que o valor da variável do lado esquerdo da equação é maior.

O objetivo é tentar fazê-lo de forma mais eficiente do que uma força bruta completa.

É isso aí.

A seguir:

Para resolver este problema, foi inventada uma técnica "evolucionária" para encontrar valores. Analogias e métodos originários do darwinismo foram construídos.

A questão da eficiência desta abordagem é discutível. Provavelmente, existem maneiras mais simples e eficazes de resolver este problema.

Minha prática prova que as abordagens geralmente aceitas nem sempre são as mais eficazes.

Tenho certeza de que podemos contornar muito bem os "evolucionistas".

Vamos tentar!

 

Um exemplo do algoritmo do participante para a segunda variante de chamar o FF:

#property library
#property strict

//+------------------------------------------------------------------+
// тестовая фитнес функция чемпионата, не известна участникам
#import "\\Projects\\OAC\\lib\\ff.ex5"
// запросить количество параметров ФФ 
int    GetParamCountFF (); 
// запуск ФФ, получеие значения соответствующее параметроам ФФ
double FF (double &array []); 
// произведённое количество запусков ФФ
int    GetCountRunsFF (); 
#import
//+------------------------------------------------------------------+

//+------------------------------------------------------------------+
void InitAO (int paramCount, int maxFFruns) export
{
  params = paramCount;
  maxFFrunsPossible = maxFFruns;
}
//+------------------------------------------------------------------+

//+------------------------------------------------------------------+
void StartAlgo () export
{
  double param []; 
  ArrayResize (param, params);
  double ffVolue = 0.0; 
  
  //------------------------------------------------------------------
  for(int i=0; i< maxFFrunsPossible; i++) 
  {
    GenerateParam (param);
    ffVolue = FF(param);
    if(ffVolue > maxFFvolue) 
      maxFFvolue = ffVolue;
  }
  //------------------------------------------------------------------
}
//+------------------------------------------------------------------+

//+------------------------------------------------------------------+
double GetMaxFF () export
{
  return(maxFFvolue);
}
//+------------------------------------------------------------------+

//!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
// Все функции выше этой строки - обязательны! Именно они будут импортированы 
// и использованы тестовым скриптом. Они нужны для доступа к алгоритму оптимизации.
// Содержимое - произвольное, на усмотрение участника
//!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!



//!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
// Ниже этой строки пример алгоритма оптимизации участника
//————————————————————————————————————————————————————————————————————
int    params     = 0;
int    maxFFrunsPossible = 0;
double maxFFvolue = - DBL_MAX;
double minParam   = -10.0;
double maxParam   = 10.0;
double stepParam  = 0.1;
//————————————————————————————————————————————————————————————————————

//————————————————————————————————————————————————————————————————————
// Генерация значений оптимизируемых параметров
void GenerateParam (double &param[])
{
  int size = ArraySize (param);
  double paramVolue = 0.0;
  for(int i = 0; i < size; i++) 
  {
    paramVolue = RNDfromCI (minParam, maxParam);
    param [i] = SeInDiSp (paramVolue, minParam, maxParam, stepParam); 
  }
}
//————————————————————————————————————————————————————————————————————

//————————————————————————————————————————————————————————————————————
// Выбор в дискретном пространстве
double SeInDiSp (double in, double inMin, double inMax, double step) 
{ 
  if(in <= inMin) 
    return (inMin); 
  if(in >= inMax) 
    return (inMax); 
  if(step == 0.0) 
    return (in); 
  else 
    return (inMin + step * (double)MathRound ((in - inMin) / step));
}
//————————————————————————————————————————————————————————————————————

//————————————————————————————————————————————————————————————————————
// ГСЧ в заданном интервале
double RNDfromCI (double min, double max) 
{ 
  if(min == max) 
    return (min); 
  double Min, Max; 
  if(min > max) 
  {
    Min = max; 
    Max = min;
  }
  else 
  {
    Min = min; 
    Max = max;
  }
  return (double(Min + ((Max - Min) * (double)MathRand () / 32767.0)));
}
//————————————————————————————————————————————————————————————————————

O código básico do algoritmo é o mesmo da primeira variante, mas com a chamada do FF a partir do algoritmo em vez de a partir do script.

Os resultados são naturalmente semelhantes aos da primeira variante:

2016.06.22 11:47:45.321 Variante 2 da OAC (GBPUSD,M30)

2016.06.22 11:47:45.321 OAC variant 2 (GBPUSD,M30) Hora: 135 µs; 0.00013500 c

2016.06.22 11:47:45.321 OAC variante 2 (GBPUSD,M30) FF Funciona: 1000

2016.06.22 11:47:45.321 Variante OAC 2 (GBPUSD,M30) Máximo: 2.94159260

2016.06.22 11:47:41.404 Variante 2 da OAC (GBPUSD,M30)

2016.06.22 11:47:41.404 OAC variant 2 (GBPUSD,M30) Tempo: 136 µs; 0.00013600 c

2016.06.22 11:47:41.404 OAC variante 2 (GBPUSD,M30) FF Funciona: 1000

2016.06.22 11:47:41.404 Variante 2 da OAC (GBPUSD,M30) Max: 3.10159260

2016.06.22 11:47:37.309 Variante 2 da OAC (GBPUSD,M30)

2016.06.22 11:47:37.309 OAC variant 2 (GBPUSD,M30) Tempo: 133 µs; 0.00013300 c

2016.06.22 11:47:37.309 OAC variante 2 (GBPUSD,M30) FF Funciona: 1000

2016.06.22 11:47:37.309 Variante 2 da OAC (GBPUSD,M30) Max: 3.06159260

2016.06.22 11:47:32.933 Variante 2 da OAC (GBPUSD,M30) ---------------------------------

2016.06.22 11:47:32.933 Variante OAC 2 (GBPUSD,M30) Tempo: 133 µs; 0.00013300 c

2016.06.22 11:47:32.933 OAC variante 2 (GBPUSD,M30) FF Funciona: 1000

2016.06.22 11:47:32.933 Variante 2 da OAC (GBPUSD,M30) Max: 3.10159260

2016.06.22 11:47:07.584 Variante 2 da OAC (GBPUSD,M30)

2016.06.22 11:47:07.584 OAC variant 2 (GBPUSD,M30) Tempo: 180 µs; 0.00018000 c

2016.06.22 11:47:07.584 OAC variant 2 (GBPUSD,M30) FF runs: 1000

2016.06.22 11:47:07.584 OAC variant 2 (GBPUSD,M30) Max: 3.04159260

Isto é - nada mal.

 

Assim, os exemplos acima mostram como os algoritmos dos participantes são conectados a scripts de teste através de funções de importação.

Deixe-me lembrar por que exatamente esta forma de trabalhar com algoritmos dos participantes é organizada: é necessário, por um lado, esconder o algoritmo do participante para proteger a propriedade intelectual e, por outro, permitir o controle e a verificação tanto pelos membros do júri quanto pelos espectadores.

 

Vou testá-lo hoje.

Mas seria aconselhável compilar (eu entendo, Andrei, que você estava com pressa) e em um só post, publicar as regras relativas aos arquivos, com anexos destes mesmos arquivos. Não necessariamente neste momento, mas para ter um ponto de partida.

 
Реter Konow:

Agora, quero apelar para todos os participantes, que se consideram "recém-chegados" neste assunto e não esperam seriamente ganhar.

Se abandonarmos toda a "teoria" insana sobre múltiplas dimensões do espaço, que confunde de forma selvagem um problema já confuso, e nos voltarmos para a matemática pura, vemos que a FF é uma equação.

Esta equação torna-se uma função analítica somente se aplicada a um gráfico.

Mas há uma pergunta - DEVERIA SER? - Um gráfico simplesmente ajuda a visualizar os padrões de relacionamento dos parâmetros da equação.

Após 158 páginas de discussão, já podemos formular a essência do problema:

Precisamos encontrar os valores das variáveis do lado direito daequação em que o valor da variável do lado esquerdo da equação é maior.

O objetivo é tentar fazê-lo com mais eficiência do que uma enumeração completa.

É isso aí.

A seguir:

Para resolver este problema, foi inventada uma técnica "evolucionária" para encontrar valores. Analogias e métodos originários do darwinismo foram construídos.

A questão da eficiência desta abordagem é discutível. Provavelmente, existem maneiras mais simples e eficazes de resolver este problema.

Minha prática prova que as abordagens geralmente aceitas nem sempre são as mais eficazes.

Tenho certeza de que podemos contornar muito bem os "evolucionistas".

Vamos tentar!

Se você deixar de lado a conotação emocional do cargo, o que você disse é basicamente verdade. A única coisa que você esqueceu de mencionar é que a própria equação FF é desconhecida dentro do campeonato dado (em vida pode ou não ser conhecida).

Sobre "teorias de não-ficção" - Dei neste tópico dicas claras sobre os princípios do algoritmo de otimização que não são usados em nenhum outro lugar e nunca foram usados antes (pelo menos em fontes disponíveis). E a escolha é sempre do pesquisador - como e o que ele vai usar no algoritmo. No exemplo acima está um algoritmo que não tem nada a ver com Darwin, mesmo indiretamente. Há muitos métodos de otimização e ninguém, pelo menos eu não afirmei que "originário de Darwin" é melhor.

Portanto, boa sorte para os iniciantes! Vá em frente, à vitória!

 
Eu não codifiquei um cinco e também não tenho experiência em operações de exportação/importação. Por favor, me diga se entendi seu exemplo corretamente. Coloquei meus comentários no código. Outra pergunta . Se o FF for dado por fórmula, haverá operações de divisão ou extração de raiz. Um valor zero ou negativo causará um erro crítico e interromperá o programa.
// -- данный код находится на стороне жюри (организатора)---------------------
#property library    //EX5-файл будет являться библиотекой
#property strict
int  countRuns    = 0;  // число обращений к ФФ. Фитнес функции это, как я понимаю неизвестная никому функция у которой 500 параметров
 // и нужно найти такие значения параметров при которой значение фф= максимальному 
//+------------------------------------------------------------------+
int GetParamCountFF () export //функция задачи участникам количества параметров фф  модификатор export указывает что функция доступна
// алгоритму участника  
{ 
  return (2);// возвращает количество параметров участнику 2 для данного примера 
  // участник в своём коде прописывает  int NumberParam=GetParamCountFF();
}

double FF (double &array []) export // сама фф 
{ 
  countRuns++;
  int sizeArray = ArraySize (array);//количество элементов массива
  //-------дальше не пойму логику----------------- 
  if(sizeArray != 2) 
    return (-DBL_MAX); 
  return (-(pow (2.4 + array [0], 2.0) + pow (array [1] - 2.3, 2.0))+3.1415926);
 //--------------вероятно нужно так --------------
    if(sizeArray != 2){ // возвращает минимальное double ( или может лучше ошибку)
    // если количество элементов в массиве пользователя не равно заданному)
    return (-DBL_MAX);
    } 
    else{ // возвращает значение функции
  return (-(pow (2.4 + array [0], 2.0) + pow (array [1] - 2.3, 2.0))+3.1415926);
  }
  //------------------------------------------------------------------
}

int GetCountRunsFF () export
{ 
  return (countRuns);// возвращает кол. обращений к фф
}
 
Yuri Evseenkov:
Não codifico em A e não tenho experiência em operações de exportação-importação. Por favor, me diga se entendi seu exemplo corretamente. Coloquei meus comentários no código. Outra pergunta . Se o FF for dado por fórmula, haverá operações de divisão ou extração de raiz. Um valor zero ou negativo causará um erro crítico e interromperá o programa.

Sim, você está correto em seu entendimento de como funciona o campeonato FF.

A única correção sobre o retorno de resultados em caso de tamanho incorreto da matriz de parâmetros - o algoritmo do participante sabe sobre o número de parâmetros FF e se ele envia a matriz de tamanho errado para o FF, é o problema do algoritmo do participante, não do FF. Pense neste ponto, se você tomar o mercado como exemplo - o mercado nunca o informará que você está usando o número "errado" de parâmetros estratégicos em sua negociação, você obterá apenas um resultado comercial negativo e pronto, sem qualquer explicação do mercado para seus erros.

Você pode substituir a palavra Teu pela palavra Nosso, e você pode substituir a palavra Teu por Nós - nada mudará e nada permanecerá verdadeiro.

 
Igor Volodin:

Vou testá-lo hoje.

Mas seria aconselhável compilar (eu entendo, Andrei, que você estava com pressa) e em um só post, publicar as regras relativas aos arquivos, com anexos destes mesmos arquivos. Não necessariamente neste momento, mas para ter um ponto de partida.

Provavelmente, seria conveniente colocar arquivos de exemplos em um armazenamento de arquivos acessível, para não saltar em busca deles, e colocar um link para o armazenamento no início da filial.

Sim, eu o farei.

Razão: