c'è qualche funzione "StringToEnum" o un'alternativa? - pagina 2

 

Ho seguito questo, ma non ho una chiara comprensione di ciò che esattamente si vuole realizzare.

Di solito ri-codifico intorno alle cose facendole in modi diversi per finire con il risultato finale che stavo cercando, le cose possono essere fatte in molti modi.

 
Marco vd Heijden:

Ho seguito questo, ma non ho una chiara comprensione di ciò che esattamente si vuole realizzare.

Di solito ri-codifico intorno alle cose facendole in modi diversi per finire con il risultato finale che stavo cercando, le cose possono essere fatte in molti modi.

Grazie Marco. Naturalmente le cose possono essere fatte in molti modi (e soluzioni), a volte devi sceglierne uno per raggiungere il tuo obiettivo, ma ci sono alcuni modi più facili di altri. In questo caso il workaround che ho preso per imitare la funzione: StringToEnum stava usando più confronti di stringhe con "if", ma come ho detto prima la funzione eval (non implementata in mql5) potrebbe aiutare ad evitare tutti quegli if, e anche aiutare sulla manutenzione perché se le costanti cambiano il loro nome allora non è necessario cambiare il blocco di if.
 

So esattamente cosa intendi, ho centinaia, a volte anche migliaia di linee if in un blocco di codice per arrivare a ciò di cui ho bisogno.

devi amare quello che fai.

 
cyberglassed:
Grazie Marco. Naturalmente le cose possono essere fatte in molti modi (e workaround), a volte devi sceglierne uno per raggiungere il tuo obiettivo, ma ci sono alcuni modi più facili di altri. In questo caso il workaround che ho preso per imitare la funzione: StringToEnum stava usando più confronti di stringhe con "if", ma come ho detto prima la funzione eval (non implementata in mql5) potrebbe aiutare ad evitare tutti quegli if, e anche aiutare sulla manutenzione perché se le costanti cambiano il loro nome allora non devi cambiare il blocco di if.

Puoi spiegare, per favore, perché hai bisogno di questo StringToEnum. Ovviamente hai una stringa con un valore enum, ma perché è su una stringa? Sono curioso di saperlo.

In altre parole, con il supporto della funzione eval(...) potremmo risolvere molte cose allo stesso tempo.

Questo non accadrà MAI, non perdere il tuo tempo con questo. La funzione Eval() è una porta aperta alla fuga di sicurezza, Metaquotes non aggiungerà tale funzione.

 
Marco vd Heijden:

So esattamente cosa intendi, ho centinaia, a volte anche migliaia di linee if in un blocco di codice per arrivare a ciò di cui ho bisogno.

devi amare quello che fai.

Il tuo problema NON può essere risolto con una StringToEnum(), lo sai già (credo).
 
Alain Verleyen:
Il tuo problema NON può essere risolto con una StringToEnum(), lo sai già (credo).

Corretto, ma può essere fatto al contrario.

  int b=0;
  
  if(EnumToString(MODE_SMMA)=="MODE_SMMA"){b=2;Print("b= ",b);}

Ma non avrebbe senso dato che MODE_SMMA ha già il valore intero 2, ecco perché ho scritto che non capisco cosa sta cercando di fare cyberglassed.

 
Marco vd Heijden:

Corretto, ma può essere fatto al contrario.

Ma non avrebbe senso dal momento che MODE_SMMA ha già il valore intero 2 che è il motivo per cui ho scritto che non capisco cosa cyberglassed sta cercando di realizzare.

Marco il workaround che uso è qualcosa come il seguente (versione molto minimalista):

int StringToEnum(string strId) {
        if (false) {}
        else if (strId == "PRICE_CLOSE")     return 1;
        else if (strId == "PRICE_OPEN")      return 2;
        else if (strId == "PRICE_HIGH")      return 3;
        else if (strId == "PRICE_LOW")       return 4;
        else if (strId == "PRICE_MEDIAN")    return 5;
        else if (strId == "PRICE_TYPICAL")   return 6;
        else if (strId == "PRICE_WEIGHTED")  return 7;
        // ...
        return -1;
}

void OnStart() {
        string strId = "PRICE_MEDIAN";
        printf("%s: %d ", strId, StringToEnum(strId));
}

ovviamente non parto dalla costante, parto da una stringa, ti dico questo perché sul tuo codice hai scritto quanto segue:

EnumToString(MODE_SMMA)

come se tu avessi dall'inizio la costante stessa.

Scusa se ti ho capito male, il mio inglese non è troppo buono.

Saluti.

 
Alain Verleyen:

Puoi spiegare, per favore, perché hai bisogno di questo StringToEnum. Ovviamente hai una stringa con un valore enum, ma perché è su una stringa? Sono curioso di saperlo.

In altre parole, con il supporto della funzione eval(...) potremmo risolvere molte cose allo stesso tempo.

Questo non accadrà MAI, non perdete il vostro tempo con questo. La funzione Eval() è una porta aperta alla fuga di sicurezza, Metaquotes non aggiungerà tale funzione.

Ciao Alain, ho soddisfatto la tua curiosità :P

Immagina di utilizzare più codici esterni di mql5, quindi hai a che fare con più tipi di dati "enum" definiti su di essi, e naturalmente, come un umano, è meglio per te ricordare il nome della stringa di ogni valore di ogni "enum". Poi in alcune parti vuoi specificare qualche valore di qualche enum in formato stringa, allora non puoi farlo direttamente, quindi devi usare qualche workaround come ho scritto sopra. Questo ha due grossi svantaggi, il primo è che devi raccogliere tutti i valori di tutti gli enum coinvolti e il secondo svantaggio è la manutenzione, quindi se aggiorni qualche codice mql5 esterno dove lo sviluppatore ha cambiato il valore int associato a qualche rappresentazione costante allora potresti ottenere un comportamento inaspettato, quindi devi continuare a controllare gli aggiornamenti del codice.

Riguardo all'argomento della fuga di sicurezza... Non sono totalmente d'accordo con quello che hai detto sul fatto che sia una porta aperta alla fuga di sicurezza. Certamente potrebbe essere una porta aperta, ma tu come programmatore devi impostare i limiti e prendersi cura di possibili situazioni critiche, voglio dire che puoi gestire perfettamente tali situazioni come in PHP, anche su SQL con l'iniezione di codice dove devi analizzare alcuni dati critici possibili in ingresso dagli utenti nel caso in cui abbiano accesso al tuo codice.

Forse in futuro avremo un po' di fortuna e il team di sviluppatori potrà darci qualche aiuto in questa direzione, quindi per ora, possiamo usare dei workaround :P

 
cyberglassed:

Marco il workaround che uso è qualcosa come il seguente (versione molto minimalista):

ovviamente non parto dalla costante, parto da una stringa, ti dico questo perché sul tuo codice hai scritto quanto segue:

come se tu avessi fin dall'inizio la costante stessa.

Scusa se ho capito male, il mio inglese non è molto buono.

Saluti.

È per questo che si chiama a ritroso e si comincia a confrontare tutte le enumerazioni per sciogliere il valore dell'enum dalla stringa.

int b;
if(EnumToString(MODE_SMA)=="MODE_SMA"){b=0;}
if(EnumToString(MODE_EMA)=="MODE_EMA"){b=1;}
if(EnumToString(MODE_SMMA)=="MODE_SMMA"){b=2;}
if(EnumToString(MODE_LWMA)=="MODE_LWMA"){b=3;}

Print(b);


ma non è la stessa cosa?

non importa da che parte confronti la stringa se c'è una corrispondenza segnerà il valore in b.

int b;
if("MODE_SMA"==EnumToString(MODE_SMA)){b=0;}
if("MODE_EMA"==EnumToString(MODE_EMA)){b=1;}
if("MODE_SMMA"==EnumToString(MODE_SMMA)){b=2;}
if("MODE_LWMA"==EnumToString(MODE_LWMA)){b=3;}

Print(b);

Quindi qui partiamo da un valore di stringa, ma qual è la differenza?

Nessuna.

 
Marco vd Heijden:

...

ma non è la stessa cosa?

non importa da che parte confronti il pungiglione se c'è una corrispondenza segnerà il valore a b.

int b;
if("MODE_SMA"==EnumToString(MODE_SMA)){b=0;}
if("MODE_EMA"==EnumToString(MODE_EMA)){b=1;}
if("MODE_SMMA"==EnumToString(MODE_SMMA)){b=2;}
if("MODE_LWMA"==EnumToString(MODE_LWMA)){b=3;}

Print(b);

Quindi qui partiamo da un valore di stringa, ma qual è la differenza?

Nessuna.

il tuo codice sopra è inutile perché restituirà sempre "b = 3" (ultimo "if" perché non stai usando "else if")

se usate "else if", allora restituirà sempre "b = 0".

comunque, l'informazione: "b = 3" ogni volta, non dà nessuna informazione.