devo alcuni alberi di ereditarietà di base:Come risolvere quale funzione viene chiamata in base al tipo di oggetti in un contenitore?
class Base {
virtual double func() = 0;
// functionality is not important for the problem
// but it's good to know that Base has some virtual functions
};
class DerivedA : public Base {
virtual double func() {}; // implementation A
};
class DerivedB : public Base {
virtual double func() {}; // implementation B
};
ho un recipiente contenente un puntatore a uno o DerivedA
DerivedB
istanze.
void f1(std::vector<Base*> a)() { /* some code */ }
int main(in, char**) {
std::vector<Base*> base_container;
f1(base_container); // works fine
}
Quasi tutto funziona sulla base, ma ho qualche funzione, non specificato nel DerivedA
o DerivedB
, vale a dire l'attuazione specifica, ma funziona su un contenitore DerivedA
o DerivedB
. Supponiamo che il seguente frammento di codice:
void f2(std::vector<DerivedA*> a)() { /* implementation A specific code */ }
void f2(std::vector<DerivedB*> a)() { /* implementation B specific code */ }
Qual è la procedura migliore per chiamare la funzione corretta? Elencho alcune possibili soluzioni, che mi sono venute in mente, ma presentano tutti i maggiori inconvenienti.
Potrei contenere tutti i dati in contenitori di implementazione specifici. Tuttavia,
f1()
non funzionerà più poichéstd::vector<DerivedA*>
non è un figlio distd::vector<Base*>
(per buoni motivi!).Potrei lanciare manualmente tutti gli oggetti tutto il tempo, ma quello è brutto.
Potrei chiamare manualmente la funzione corretta che si aspetta un contenitore di Base dando loro un nome distintivo (come
f2_a
ef2_b
), ma sembra brutto.Potrei implementare f2 come specializzazione di template di funzioni, ma ciò sembra offensivo.
Potrei provare a far dipendere la funzione sul contenitore solo dalle funzioni degli oggetti nel contenitore e quindi implementare per loro funzioni sovraccariche. Questa è una buona soluzione in molti casi, ma nel mio caso è davvero una funzione sul contenitore, dando diverse implementazioni sul contenitore per
DerivedA
eDerivedB
, non solo iterando sul contenuto del contenitore.
Come implementereste tale cosa? Come posso ottenere un container che può essere passato sia a f1()
sia a f2()
?
Cosa farebbe 'f2()' per un contenitore che conteneva due oggetti, uno un 'DerivedA' e l'altro un' DerivedB'? –
Potresti fornire un esempio del perché questo potrebbe essere utile? Non riesco a vederlo.Da un punto di vista OO, questo sembra essere disordinato. Questo potrebbe essere il motivo per cui i tuoi approcci si rivelano ugualmente brutti? –
Potresti avere ragione. Sono nel machine learning niché. Quindi la mia base è un modello predittivo, mentre le classi derivate sono modelli di regressione o classificazione. Ora voglio calcolare le misure di accuratezza dei modelli e differiscono dalla classificazione e dalla regressione. – hildensia