Errori, bug, domande - pagina 1891

 
Renat Fatkhullin:

Certo.

Sei sicuro? Perché dynamic_cast è più spesso usato per la conversione dal basso verso l'alto, dal genitore alla prole.

Inoltre, in MQL lancia perfettamente dal basso verso l'alto, anche quando non dovrebbe:

class A
{
public:
   virtual void f()
   {
      Print("1");
   }
};

class B: public A
{
public:
   virtual void f()
   {
      Print("2");
   }
};

void OnStart()
{
   A* ptr1 = new B();
   ptr1.f();
   A* ptr2 = new A();
   ptr2.f();
   
   B* casted = dynamic_cast<B*>(ptr1);
   casted.f();
   
   B* casted1 = dynamic_cast<B*>(ptr2);
   casted1.f(); // здесь должна быть ошибка потому что casted1 должен быть null
   delete ptr1;
   delete ptr2;
}

вывод:
2017.05.13 18:30:14.864    t ETHUSD,M5: 2
2017.05.13 18:30:14.865    t ETHUSD,M5: 1
2017.05.13 18:30:14.866    t ETHUSD,M5: 2
2017.05.13 18:30:14.867    t ETHUSD,M5: 2


Renat Fatkhullin:

Date un'occhiata al frammento di codice MQL5 discusso.

Sì, non dovrebbe funzionare ed è già spiegato sopra, ma non perché il cast bottom-up sia impossibile.

 
Konstantin:
Se lanciamo il puntatore dall'alto verso il basso, cioè verso il genitore, dopo di che passiamo il puntatore da qualche altra parte nello scope, i campi del discendente saranno disponibili lì?

Sì, ecco un esempio che dimostra la tua domanda:

class CLASS1
  {
public:
   int               i;
  };
class CLASS2 : public CLASS1
  {
  };
void OnStart()
  {
   CLASS1 _object;
   CLASS2 *_ptr=dynamic_cast<CLASS2 *>(&_object);

   if(!_ptr)
      Print("CLASS1 -> CLASS2 failed, null");

   CLASS2 *my=new CLASS2;
   CLASS1 *my_ptr=my;
   CLASS2 *my_ptr2=dynamic_cast<CLASS2 *>(my_ptr);

   if(my_ptr2)
     {
      Print("CLASS2 -> CLASS1 -> CLASS2 ok");
      my_ptr2.i=1;
     }
   Print("Value: ",my.i);
  }
e uscita:
2017.05.13 18:34:50.341 cast (EURUSD,H1)        CLASS1 -> CLASS2 failed, null
2017.05.13 18:35:18.933 cast (EURUSD,H1)        CLASS2 -> CLASS1 -> CLASS2 ok
2017.05.13 18:35:20.110 cast (EURUSD,H1)        Value: 1

Per prima cosa, controlliamo il cast non risolto dal basso verso l'alto e otteniamo NULL. Questo è corretto.

Poi creiamo un oggetto CLASS2, assegniamo un riferimento ad esso alla sua classe madre (qui è importante capire che dinamicamente l'ambiente sa che il tipo originale dell'oggetto CLASS2 è memorizzato nelle sue meta-informazioni). Poi (solo la tua domanda) fare un cast dinamico (con il giusto controllo di conversione basato sulle metainformazioni dell'oggetto sorgente) dal riferimento CLASS1 a CLASS2.

Controlliamo il risultato del casting e lo scriviamo nella variabile i = 1. Infine emettiamo il valore di i, facendo riferimento all'oggetto originariamente creato.

Tutto funziona correttamente e secondo le specifiche (inclusa la specifica dynamic_cast del C++ stesso).

 
Комбинатор:

Sei sicuro? Perché dynamic_cast è più spesso usato per la conversione dal basso verso l'alto, dal genitore alla prole.

Inoltre, in MQL lancia perfettamente dal basso verso l'alto, anche quando non dovrebbe:

Esattamente:

Non dimenticate di aggiornare alle ultime build. Attualmente sto testando sul 1598, che è stato recentemente postato come versione zippata in questo thread, credo.

 
Renat Fatkhullin:

Non dimenticate di aggiornare alle ultime build.

Sì, la vecchia costruzione.

Renat Fatkhullin:

Esatto, non si può guidare dal basso verso l'alto, ma solo dall'alto verso il basso. Questo è per la sicurezza.

Dovresti cancellare questo, è fuorviante e contraddice direttamente il funzionamento di dynamic_cast
 
Комбинатор:

Sì, la vecchia costruzione.

Questa la cancellate, è fuorviante e contraddice direttamente il funzionamento di dynamic_cast

Nell'ambito dell'esempio di fusione testa a testa CLASSE1 -> CLASSE2 sollevato, hai capito bene. Questo è il tipo di casting che la maggior parte delle volte la gente ha in testa.

Inoltre, è il "non puoi lanciare dal basso verso l'alto, solo dall'alto verso il basso" che è il cuore del controllo di sicurezza dynamic_cast.

Chi sa cosa sta facendo capisce l'essenza del dynamic_casting.

 
Renat Fatkhullin:

Non dimenticate di aggiornare alle ultime build. Attualmente sto testando sul 1598, che è stato recentemente postato come zip in questo thread, credo.

In quale file exe si trova il compilatore e l'esecutore?

In questo momento MT4b1080 sta eseguendo MEb1599. Per favore, spiega cosa fanno metaeditor.exe e terminal.exe.

 
fxsaber:

In quale file exe si trova il compilatore e l'esecutore?

L'MT4b1080 ora sta eseguendo MEb1599. Per favore, spiega cosa fanno metaeditor.exe e terminal.exe.

Il compilatore è lo stesso per entrambe le piattaforme. È in metaeditor.exe
 
Renat Fatkhullin:
Il compilatore per entrambe le piattaforme è lo stesso. È in metaeditor.exe
E l'executor, che controlla lo stesso dynamic_cast, in terminal.exe?
 
fxsaber:
E l'executor, che controlla lo stesso dynamic_cast, in terminal.exe?
Naturalmente
 
Renat Fatkhullin:
Un'altra domanda come questa

Forum sul trading, sistemi di trading automatico e test di strategie di trading

Bug, bug, domande

fxsaber, 2017.05.11 13:26

Perché EX5 tale codice
void OnStart() {}

Pesa 5kb?