Im Konstruktor Initialisierung von Objekt entscheiden
-
Hallo ihr Lieben,
ein kleines Minimalbeispiel:
In der Klasse
dummyin Zeile 21 wird in Zeile 26 bzw. 27 ein Objekt_dinitialisiert, dass entweder nach der Blaupause vonfoooderbarentworfen wird. Dies kann ich durch auskommentieren steuern.Jetzt aber die Frage: Kann ich das nicht auch über den Konstruktor entscheiden? Also ich initialisiere z.B. die Klasse
dummymittelsdummy d(bar)und dadurch wird_danhand vonbarinitialisiert?#include <iostream> class foo { public: foo():_d(1.0){} double operator()(){ return _d; } private: double _d; }; class bar { public: bar():_d(2.0){} double operator()(){ return _d; } private: double _d; }; class dummy { public: double operator()(){ return _d(); } private: foo _d; //bar _d; }; int main() { dummy d; std::cout << d() << std::endl; return 0; }Gruß,
-- Klaus.
-
Ja, das geht. Aber nicht so, wie du es jetzt hast.
Denn du kannst den Typen von _d nicht ohne weiters nach bar oder foo ändern.
Dafür braucht man Vererbung und Polymorphie.
-
da foo und bar nicht polymorph sind, steht auch zu compilezeit fest, welchen typ das argument hat, mit welchem du den konstruktor aufrufst. folglich kann man schreiben:
template<typename T> class dummy { T _d; public: explicit dummy(T const& Rhs) : _d(Rhs) { } double operator()(){ return _d(); } };ich weiss, das ist etwas mühsam dass man immer den typen explizit angeben muss aber es hat dafür keinen laufzeit-overhead.
-
Wollte gerade ein Template-Codebeispiel posten, gerade noch rechtzeitig gesehen, dass mir schon jemand die Arbeit abgenommen hat

In dem geposteten Beispiel sollte der Template-Parameter automatisch ermitelt werden können, eine explizite Angabe sollte nicht nötig sein.
-
Für mich klang das so, dass er das zur Runtime entscheidet haben möchte, bpsw. via einem bool Flag oder so.
Naja, mal gucken, was er dazu sagt.
-
daddy_felix schrieb:
In dem geposteten Beispiel sollte der Template-Parameter automatisch ermitelt werden können, eine explizite Angabe sollte nicht nötig sein.
ich bin mir jetzt nicht 100% sicher aber ich glaube, dass klassen-template-argumente nicht anhand des konstruktors deduziert werden (können). ansonsten könnte man
decltypeschon in c++03 implementieren.
-
asfdlol schrieb:
daddy_felix schrieb:
In dem geposteten Beispiel sollte der Template-Parameter automatisch ermitelt werden können, eine explizite Angabe sollte nicht nötig sein.
ich bin mir jetzt nicht 100% sicher aber ich glaube, dass klassen-template-argumente nicht anhand des konstruktors deduziert werden (können). ansonsten könnte man
decltypeschon in c++03 implementieren.Du kannst dir 100% sicher sein.
Schließlich müssen die Parameter des Klassentemplates bekannt sein, um überhaupt erst ermitteln zu können, welche Konstruktoren die jeweilige Spezialisierung hat.Klaus82 schrieb:
Jetzt aber die Frage: Kann ich das nicht auch über den Konstruktor entscheiden? Also ich initialisiere z.B. die Klasse
dummymittelsdummy d(bar)und dadurch wird_danhand vonbarinitialisiert?Im Prinzip schon, falls du C++11 verwendest. Allerdings sollte das sehr gut überlegt sein, weil dann die Speicherverwaltung in der Klasse selbst implementiert werden muss.
ungefähr so:
class dummy { public: dummy(foo x) : is_foo(true), foo_d{x} {} dummy(bar x) : is_foo(false), bar_d{x} {} dummy(const dummy& other) : is_foo(other.is_foo) { is_foo ? (void*)new((void*)&foo_d)foo(other.foo_d) : (void*)new((void*)&bar_d)bar(other.bar_d); } dummy& operator=(const bar& rhs) { ... } ~dummy() { is_foo ? foo_d.~foo() : bar_d.~bar(); } double operator()(){ return is_foo ? bar_d() : foo_d(); } private: bool is_foo; union { foo foo_d; bar bar_d; }; };wahrscheinlich falsch, sollte aber das Prinzip klarmachen. In 95% der Fälle dürfte es eine schlechte Idee sein.