Número mágico automático - página 4

 
cloudbreaker:

Me fez pensar que seria útil documentar (muito concisamente):

1. Critérios para a decisão de implementar números mágicos

2. Critérios para decidir usar a geração automática de números mágicos

3. Critérios para a decisão de implementar uma camada de persistência

4. Critérios para decidir sobre globais vs. acesso a arquivos por persistência

Respostas breves, inteiramente pessoais...


(2) depende de qualquer número de fatores, incluindo se o usuário quer ser capaz de controlar os números mágicos para que possa usá-los como uma forma de agrupar os resultados de diferentes estratégias.

(3) é algo que eu evitaria se pudesse, mas quase nunca consigo (ver "variáveis externas e mudança de tempo?"). Seria bom se o MT4 fornecesse ajuda para persistir e recuperar o estado de EAs. Mas não ajuda.

(4) leva a uma preferência pessoal bastante forte: Eu não gosto de globais. Os usuários podem apagá-los; o armazenamento é limitado a números; e o formato dos gvariables.dat é obscuro. Eu prefiro muito arquivos que, como último recurso, se necessário, podem ser modificados usando um editor de texto.


- Só me restam 8 posts antes de fazer uma pausa por um tempo.

Vejo que você acertou o número mágico. Como pelo menos vai estar quente onde você está...

 

Eu tenho trabalhado nesta idéia de vez em quando, e finalmente consegui fazer o que queria. Aqui está um gerador de números mágicos que pega o código ASCII do símbolo e o adiciona ao período de tempo e um código personalizado para gerar um número mágico que é exclusivo para o período de tempo, símbolo e EA. Se eu soubesse de uma maneira de a EA ler seu próprio nome, eu usaria o ASCII desse código em vez do código personalizado. Mas com essa fraqueza, acho que se encaixa nos critérios acima - estaria bem com uma falha no sistema porque escolheria o mesmo número que escolheu anteriormente na reinicialização do sistema. O ponto fraco que pude ver é que ele escolheria números mágicos duplicados se comercializasse mais de uma instância da mesma EA no mesmo período de tempo e símbolo.

Eis o que eu tenho:

string GetSymbol=Symbol();
int MNSymbol,MNSymbolCalc,MagicNumber;
for(int a=0;a<6;a++)//turn the Symbol() into an ASCII string and add each character into MNSymbol
{
MNSymbolCalc=StringGetChar(GetSymbol, a);
MNSymbolCalc=((MNSymbolCalc-64)*(MathPow(10,(a))));//subtract 64 b/c ASCII caracteres começam em 65, multiplicar o resultado pelo a-th power for cleanness (desnecessário porém)
MNSymbol = MNSymbol+MNSymbolCalc;
}
int MNPeriod=Period();

int MNEACode=100000;//Make this number different for each EA to prevent two different types of EA's choose the same Magic Number
MagicNumber=MNSymbol+MNPeriod+MNEACode;

 

JT, sim... "problemas" de duplicação são coisas de pesadelos ;)


Como você e eu suspeitamos que muitos, a questão da singularidade é um tema recorrente constante que é atacado como e quando, mas de alguma forma nunca parece certo!

Meu código publicado anteriormente neste tópico foi substituído por abaixo, que pode ser útil (se não for por outra razão que não seja para uma boa risada :).

***Note a cadeia de nomes EA disponível via chamada para construir.

Nos esforços para fazer multi ccy,por existem funções locais usadas. ou seja, farto de codificar sempre o mesmo código de cabeçalho de função para verificar se há atualidades vazias: ccy,per

daí meu uso de _Símbolo() e _Periodo(). Considerações de velocidade/tamanho imho, mesmo no MT4 interprete não vale a pena as energias para se preocupar com...

De qualquer forma, talvez isto dê que pensar...


meu raciocínio para fazer abaixo [e doc'd em função] é:

Esta é uma maneira útil de garantir que SE uma EA parar em uma CCY,PER que ao executá-la novamente mais tarde contra a mesma CCY,PER

gerará giExpertId idêntico (aka, Magic#). Significa que poderá retomar a gestão de negócios pendentes no pool.

Outro chamado EA pode funcionar no mesmo ambiente gráfico sem medo de duplicar valores.

Portanto, a OrderPools terá bilhetes com um Magic# específico da EA, permitindo apenas o mapeamento por EA dos seus bilhetes.


Seu comentário sobre >1 'mesmo nome' EA no mesmo ccy,per é de fato um problema. Finalmente decidi que HEY! se eu cometer este erro, então mereço um pontapé na traseira por ser tão irrefletido, rs

No final, como mostrado nesta linha, existem zilhões de idéias/métodos, cada um com seus pontos fortes e fracos.

Tudo se resume a obter [pelo menos] um dado único sempre que uma EA funciona e isso [para mim] é a questão kernal.

Eu nunca pensei muito sobre a queda da EA/CT que leva ao reinício e a lata de vermes se refere a pegar de onde parou. Isso é resolvido agora, desde que os autógenos EA sejam EAid/magic# com dados que sejam exclusivos do seu ambiente gráfico R/T. Ele sempre gera o mesmo número...

oh bem, divirtam-se!


int iMakeExpertId (string sSymbol="",int iPeriod=EMPTY)
{

  return( iMakeHash(_Symbol( sSymbol), getPeriodStr(_Period( iPeriod)),WindowExpertName()) );

}//iMakeExpertId()
//
//
//


//+------------------------------------------------------------------+
//
int iMakeHash (string s1, string s2= EMPTYSTRING, string s3= EMPTYSTRING, string s4= EMPTYSTRING, string s5= EMPTYSTRING
			,string s6= EMPTYSTRING, string s7= EMPTYSTRING, string s8= EMPTYSTRING, string s9= EMPTYSTRING, string s10= EMPTYSTRING)
{
  /*
  Produce 32bit int hash code from  a string composed of up to TEN concatenated input strings.
  WebRef: http://www.cse.yorku.ca/~oz/hash.html
  KeyWrd: "djb2"
  FirstParaOnPage:
  "  Hash Functions
  A comprehensive collection of hash functions, a hash visualiser and some test results [see Mckenzie
  et al. Selecting a Hashing Algorithm, SP&E 20(2):209-224, Feb 1990] will be available someday. If
  you just want to have a good hash function, and cannot wait, djb2 is one of the best string hash
  functions i know. it has excellent distribution and speed on many different sets of keys and table
  sizes. you are not likely to do better with one of the "well known" functions such as PJW, K&R[1],
  etc. Also see tpop pp. 126 for graphing hash functions.
  "

  NOTES: 
  0. WARNING - mql4 strings maxlen=255 so... unless code changed to deal with up to 10 string parameters
     the total length of contactenated string must be <=255
  1. C source uses "unsigned [char|long]", not in MQL4 syntax
  2. When you hash a value, you cannot 'unhash' it. Hashing is a one-way process.
     Using traditional symetric encryption techniques (such as Triple-DES) provide the reversible encryption behaviour you require.
     Ref:http://forums.asp.net/t/886426.aspx subj:Unhash password when using NT Security poster:Participant
  //
  Downside?
  original code uses UNSIGNED - MQL4 not support this, presume could use type double and then cast back to type int.
*/
  string s = StringConcatenate( s1, s2, s3, s4, s5, s6, s7, s8, s9, s10);
  int iHash = 5381;
  int iLast = StringLen( s)-1;
  int iPos=0;

  while( iPos <= iLast )		//while (c = *str++)	[ consume str bytes until EOS hit {myWord! isn't C concise! Pity MQL4 is"!"} ]
  {
    //original C code: hash = ((hash << 5) + hash) + c; /* hash * 33 + c */
    iHash = (( iHash << 5) + iHash) + StringGetChar( s, iPos);		//StringGetChar() returns int
    iPos++;
  }
  return(MathAbs( iHash));
}//iMakeHash()
 
fbj:
  NOTES: 
  0. WARNING - mql4 strings maxlen=255 so... unless code changed to deal with up to 10 string parameters
     the total length of contactenated string must be <=255

Embora eu pessoalmente prefira o ajuste manual do número mágico, sua solução é bastante elegante. Belo código.


Uma correção - as constantes de string têm comprimento máximo de 255, as variáveis de string podem ser muito maiores, veja -> https://www.mql5.com/en/forum/123551.

 

Graças a Gordon, o código parece funcionar bem, mas no final certamente não é à prova de bala se eu executar a mesma EA no mesmo ambiente gráfico - então sim... o ajuste manual da magia# é o último método infalível - sem dúvida!


Para mim as cordas sempre foram uma dor na retaguarda. No entanto, a maioria de tudo é possível através da construção gradual de um conjunto de ferramentas, cada uma utilizando funcionalidades de ferramentas de nível inferior.

Além disso, lembro-me de irusoh1 dizer/recordar um que "é isto", então viva com ele... Bem, para mim, sempre me lembro daquele primeiro parágrafo em seu conteúdo post e está * sempre* em minha mente sempre que chego a apontar com MT onde a vontade solta de viver :))


A MQL4 online/offline fala sobre tipos de dados básicos. O link de string em ambos vai para constantes de string e todos nós sabemos o que diz aquela página do doc... ou seja, 255bytes.

Eu entendo completamente o que você está dizendo, mas a linha 29373 é, assim como a MQL4, inconclusiva e como jjc e, sem dúvida, muitos outros experimentaram - um tanto quanto incerta.

Não é possível localizar qualquer documentação que suporte a utilização total do formato da estrutura de 8bytes, caso haja documentação que suporte cordas mais longas, seria de interesse.

De qualquer forma, eu tive no passado problemas insolúveis usando cordas, então eu prefiro apenas me ater ao que os documentos dizem e trabalhar em torno disso - se necessário.

 
fbj:

A MQL4 online/offline fala sobre tipos de dados básicos. O link de string em ambos vai para constantes de string e todos nós sabemos o que diz aquela página do doc... ou seja, 255bytes.

Entendo completamente o que você está dizendo, mas o fio 29373 é, assim como o manuseio de cordas MQL4, inconclusivo e como a jjc e sem dúvida muitos outros experimentaram - um pouco incerto

Não é possível localizar qualquer documentação que suporte a utilização total do formato da estrutura de 8bytes, caso haja documentação que suporte cordas mais longas, seria de interesse.

De qualquer forma, eu tive no passado problemas insolúveis usando cordas, então eu prefiro apenas me ater ao que os documentos dizem e trabalhar em torno disso - se necessário.

Manter o máximo de 255 é obviamente a solução segura, embora eu tenha bastante código que ignora este limite e nunca tenha encontrado nenhum problema. Mas também este código é, em sua maioria, não-crítico.

Sei que a documentação é um pouco obscura sobre este assunto, mas se você tentar navegar nos fóruns russos (com a tradução do Google) lembro-me de ler um comentário oficial de um dos moderadores que as variáveis de string suportam mais de 255bytes, mas parece que não consigo encontrá-lo agora... Oh bem, acho que "é isso" e temos que viver com isso :)

 
fbj:

Não é possível localizar qualquer documentação que suporte a utilização total do formato da estrutura de 8bytes, caso haja documentação que suporte cordas mais longas, seria de interesse.

De qualquer forma, eu tive no passado problemas insolúveis usando cordas, então eu prefiro apenas me ater ao que os documentos dizem e trabalhar em torno disso - se necessário.

"O comprimento de uma constante de cordas está entre 0 e 255 caracteres. Se a constante de corda for mais longa, os caracteres supérfluos à direita serão rejeitados, e o compilador alertará de forma correspondente.

Sua representação interna é uma estrutura de 8 bytes. O primeiro elemento da estrutura é um número inteiro longo que contém o tamanho do buffer distribuído para a linha. O segundo elemento da estrutura é um endereço de 32 ordens do buffer que contém a linha".

Citado do dicionário MetaEditor Tipos de dados - Constantes de seqüência de caracteres

coisas fascinantes...

 

Eu sei que este tópico é antigo, mas vejo que todos têm uma maneira própria de obter um "número mágico" ou o que quer que você queira chamar-lhe. Também vi que alguém queria que ali a EA pudesse ler seu próprio nome...bem, isto é o que eu uso para obter o nome da minha EA

Colocar isto no topo da EA:

#define EAName "Coloque o nome da EA aqui".

Quando seu controle de pedidos em aberto faz isto:

if (OrderType() <= OP_SELL && OrderSymbol() == Symbol() && OrderComment() == EAName && OrderMagicNumber() == MagicNumber)

Pois quando sua profissão for colocada, certifique-se de tê-la para que ela coloque o EAName para um comentário como este:

Ticket = OrderSend(Symbol(), OP_BUY, Lots, Ask, Slippage, 0, 0, EAName, MagicNumber, 0, Blue);

Então, se você quiser um número mágico que você faria se quisesse executar o EA no mesmo par, mas TFs diferentes ao mesmo tempo.........., basta usar o seguinte:

int MagicNumber = Período();