Funktionszeiger: Array
-
Hallo,
Ich versuche in dem dargestellten Beispiel, eine Class mit einem Array von Funktionszeigern zu anderen Classes zu erstellen.
Beschwert sich der Compiler über den Ausdruck in Line 22 der 'test1.cpp'.Habe ich an irgendeiner Stelle das Array falsch definiert?
Danke im Voraus!
// test1.h #include <iostream> class Caller; typedef void (Caller::*functpointer)(); class Caller { public: Caller(); ~Caller(); functpointer array1[]; }; class Functions { void a(); void b(); public: Functions::Functions(); Functions::~Functions(); friend class Caller; };
// test1.cpp #include "test1.h" using namespace std; Functions::Functions() {}; Functions::~Functions() {}; void Functions::a(){ cout << "a is called" << endl; } void Functions::b(){ cout << "b is called" << endl; } Caller::Caller(){ array1[] = { &Functions::a , &Functions::b }; }; Caller::~Caller() {};
// main.cpp #include "test1.h" using namespace std; int main(){ Caller class1; }
-
Die Syntax ist falsch. Du kannst das Array so nicht initialisieren, sondern musst jedes Element explizit zuweisen. Außerdem muss die Größe des Arrays bekannt sein.
// deklaration des arrays class Caller { functpointer array1[2]; }; // konstruktor Caller::Caller() { array1[0] = &Functions::a; array1[1] = &Functions::b; };
Mit einer kleinen Änderung geht es eleganter:
// deklaration class Caller { static functpointer array1[2]; }; // implementierung functpointer Caller::array1[2] = { &Functions::a, &Functions::b };
Ist dann aber für alle Caller-Instanzen das gleiche Array!
Und das funktioniert in jedem Fall sowieso nur, wenn unda
undb
statische Memberfunktionen sind, sonst fliegt es dir wieder um die Ohren, weil die Aufrufkonventionen nicht passen.
-
Vielen Dank für Deine Antwort!
Sobald ich Deine beschriebenen Änderungen übernehme, beschwert sich der Compiler erneut über die Zeilen 10 und 11.
"cannot convert ‘void (Functions::)()’ to ‘void (Caller::)()’ in assignment".// deklaration des arrays class Caller { functpointer array1[2]; }; // konstruktor Caller::Caller() { array1[0] = &Functions::a; array1[1] = &Functions::b; };
Ich verstehe nicht ganz, warum es Probleme mit dem Scope der Funktionen gibt.
-
Das ist nicht wirklich ein Problem des Scopes. Das Array das du deklarierst, ist ein Array, das Zeiger auf Memberfunktionen der Klasse Caller, die keine Parameter nehmen und void zurückgeben, enthält.
Du kannst naheliegenderweise dann NICHT Zeiger auf Memberfunktionen einer ANDEREN Klasse in das Array stecken.
Felix
EDIT: Und natürlich musst du die Größe des Arrays schon bei der Deklaration angeben!
EDIT2: Achso, hast du ja schon geändert.Wenn du die Änderung von meinem Nachposter machen willst, musst du natürlich die andere Klasse forward-deklarieren.
-
Ah, ich hab vorhin deine Deklaration der Funktionspointer überlesen. Dein Array will
Caller
-Funktionen, du gibst ihm aberFunctions
-Funktionen. Du solltest alsotypedef void (Caller::*functpointer)();
nach
typedef void (Functions::*functpointer)();
ändern.
-
Vielen Dank!
Ich habe die den Scope des Typedef geändert und schreibe nun:
typedef void (Functions::*functpointer)();
Der Scope Functions bezieht sich also auf die Funktionen, die referenziert werden und nicht auf den Scope in dem sich die Pointer selbst befinden.
Macht auch irgendwie Sinn
-
Vielen Dank!
Ich habe die den Scope des Typedef geändert und schreibe nun:
typedef void (Functions::*functpointer)();
Der Scope Functions bezieht sich also auf die Funktionen, die dadurch referenziert werden und nicht auf den Scope, in dem sich die Pointer selbst befinden.
Macht auch irgendwie Sinn