Domanda

Il CRTP è suggerito in questa domanda circa il polimorfismo dinamico. Tuttavia, questo modello è presumibilmente utile solo per il polimorfismo statico. Il design sto guardando sembra essere ostacolato speedwise da chiamate a funzioni virtuali, come accennata qui. un aumento di velocità di addirittura 2,5 volte sarebbe fantastico.

Le classi in questione sono semplici e possono essere codificati completamente in linea, ma non è noto fino runtime che verranno utilizzati classi. Inoltre, essi possono essere concatenati, in qualsiasi ordine, ammucchiando la beffa prestazioni sulla ferita.

Qualche suggerimento (compreso come il CRTP può essere utilizzato in questo caso) i benvenuti.

Modifica usare Google salta fuori una menzione di modelli di funzione. Questi sembrano promettenti.

È stato utile?

Soluzione

Sono d'accordo con m-acuto che non hai intenzione di evitare il polimorfismo runtime.

Se il valore di ottimizzazione su eleganza, provare a sostituire diciamo

void invoke_trivial_on_all(const std::vector<Base*>& v)
{
  for (int i=0;i<v.size();i++)
    v[i]->trivial_virtual_method();
}

con qualcosa di simile

void invoke_trivial_on_all(const std::vector<Base*>& v)
{
  for (int i=0;i<v.size();i++)
  {
    if (v[i]->tag==FooTag)
      static_cast<Foo*>(v[i])->Foo::trivial_virtual_method();
    else if (v[i]->tag==BarTag)
      static_cast<Bar*>(v[i])->Bar::trivial_virtual_method();
    else...
  }
}

non è abbastanza, non certo OOP (più un ritorno a quello che si potrebbe fare nel buon vecchio 'C'), ma se i metodi virtuali sono abbastanza banali si dovrebbe ottenere una funzione con nessuna chiamata (soggetto a buon compilatore e ottimizzazione abbastanza opzioni). Una variante utilizza dynamic_cast o typeid potrebbe essere leggermente più elegante / sicura ma attenzione che queste caratteristiche hanno una propria testa che è probabilmente paragonabile ad una chiamata virtuale in ogni caso.

Dove sarà più probabile vedere un miglioramento da quanto sopra è che se alcuni metodi classi sono-ops, ed è stato salvato da loro chiamata, o se le funzioni contengono codice loop-invariante comune e l'ottimizzatore riesce a issare lo fuori dal giro.

Altri suggerimenti

Polimorfismo significa letteralmente multiple (poli) formulari (trasforma). In linguaggi staticamente tipizzati (come C ++) ci sono tre tipi di polimorfismo.

  1. Adhoc polimorfismo: Questo si vede meglio in C ++ come la funzione e il metodo di sovraccarico. Lo stesso nome della funzione si legherà a diversi metodi basati sulla corrispondenza del momento della compilazione tipo di parametri della chiamata alla firma funzione o il metodo.
  2. polimorfismo parametrico: In C ++ questo è modelli e tutte le cose divertenti che potete fare con esso, come CRTP, la specializzazione, la specializzazione parziale, meta-programmazione, ecc Ancora una volta questo tipo di polimorfismo in cui lo stesso nome del modello può fare cose diverse in base sui parametri di modello è un tempo di compilazione il polimorfismo.
  3. Sottotipo polimorfismo: Finalmente questo è ciò che pensiamo quando sentiamo la parola polimorfismo in C ++. Questo è dove le classi derivate sostituiscono funzioni virtuali a specializzarsi comportamento. Lo stesso tipo di puntatore a una classe di base può avere un comportamento differente in base al tipo derivato calcestruzzo esso sta puntando. Questo è il modo per ottenere tempo di esecuzione polimorfismo in C ++.

Se non si sa fino a quando runtime che verranno utilizzate le classi, è necessario utilizzare sottotipo polimorfismo che coinvolgerà le chiamate di funzione virtuale.

chiamate di metodo virtuali hanno un piccolissimo sovraccarico di prestazioni sopra le chiamate legate in modo statico. Mi piacerebbe invitare a guardare le risposte a questo domanda SO.

Si può andare il percorso C Ole e utilizzare sindacati. Anche se anche questo può essere un casino.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top