Funktionszeiger in Klassen
-
Hallo Leute
,ich hab hier ein riessen Prob mit Funktionszeigern in einer Klasse.
Bevor ich losleg wollte ich noch sagen, dass mir der Sinn bzw. der Unsinn meines kleinen Progs schon klar ist, ich weiss auch dass ich auf ganz anderem Wege zum Ziel kommen könnte aber der Code dient einzig und allein zum lernen !.Als erses hab ich einnkleines Prog ohne Klassen mit einem Funktionszeiger gebastelt, welches auch wunder bar funktioniert
.
Man muss der Fnkt berechne nur 3 Parameter übergeben 2 Integers zum rechnen und das was damit gemacht werden soll (addieren, multiplizieren ...),
int(*waehle)(int, int) ist der Fnkt-Zeiger der dann auf die auszuführende Fnkt zeigt !Hier mal der funktionierende Code:
#include <iostream> using namespace std; int berechne(int a, int b, int(*waehle)(int, int)); int addiere(int a, int b); int multipliziere(int a, int b); int subtrahiere(int a, int b); void main() { int Z; int Y; int X; X = berechne(10, 10,multipliziere); cout << "Das Ergebnis der Multiplikation ist : " << X << endl << endl << endl; Y = berechne(20, 10, subtrahiere); cout << "Das Ergebnis der Subtraktion ist : " << Y << endl << endl << endl; Z = berechne(20, 10, addiere); cout << "Das Ergebnis der Addition ist : " << Z << endl << endl << endl; } int addiere(int a, int b) { return a + b; } int multipliziere(int a, int b) { return a * b; } int subtrahiere(int a, int b) { return a - b; } int berechne(int a, int b, int(*waehle)(int a, int b)) { return waehle(a, b); }So jetzt hab ich versucht das ganze in ne Klasse zu werfen.
Das Funktioniert leider nicht
, ich bekomme folgenden Fehler :
error C2065: 'multipliziere' : nichtdeklarierter Bezeichner 
Hier der Code:
#include <iostream> using namespace std; class cTest { public: cTest() {} ~cTest(){} int addiere(int a, int b) { return a + b; } int multipliziere(int a, int b) { return a * b; } int subtrahiere(int a, int b) { return a - b; } int berechne(int a, int b, int(*waehle)(int a, int b)) { return waehle(a, b); } }; void main() { cTest objTest; // // int Z; // int Y; // // Y = berechne(20, 10, subtrahiere); // cout << "Das Ergebnis der Subtraktion ist : " << Y << endl << endl << endl; // // Z = berechne(20, 10, addiere); // cout << "Das Ergebnis der Addition ist : " << Z << endl << endl << endl; int X; X = objTest.berechne(10, 10,multipliziere); cout << "Das Ergebnis der Multiplikation ist : " << X << endl << endl << endl; }Was ich mir unter Anderem überlegt habe ist : Die Klasse enthält einen Zeiger,
also muss ich eine tiefe Kopier machen
???
Wenn ja wie
?
Bzw. wie krieg ich den Code mit der Klasse überhaupt zum laufen
?
Bitte helft mir, mir raucht echt der Kopf
!Vielen Dank schon mal für eure Mühe

Shadow Eater
-
Wenn du Klassenmethoden verwenden willst, dann muß du die entsprechende Klasse dafür angeben:
int berechne(int a, int b, int (cTest::*waehle)(int a, int b)) { return (this->*waehle)(a, b); // hier muß ein Klassenzeiger (this) angegeben werden }Und Aufruf dann mit:
int X = objTest.berechne(10, 10, cTest::multipliziere); // hier Klasse angegebenAlternativ kannst du auch die Klassenmethoden als "static" deklarieren, dann entspricht das einfachen Funktionszeigern.
-
Hi Th,
danke für Deine schnelle Antwort, ich hab das jetzt so implementiert:
#include <iostream> using namespace std; class cTest { public: cTest() {} ~cTest(){} int addiere(int a, int b) { return a + b; } int multipliziere(int a, int b) { return a * b; } int subtrahiere(int a, int b) { return a - b; } // int berechne(int a, int b, int(*waehle)(int a, int b)) // { // return waehle(a, b); // } int berechne(int a, int b, int (cTest::*waehle)(int a, int b)) { return (*this->waehle)(a, b); // hier muß ein Klassenzeiger (this) angegeben werden } }; void main() { cTest objTest; // // int Z; // int Y; // // Y = berechne(20, 10, subtrahiere); // cout << "Das Ergebnis der Subtraktion ist : " << Y << endl << endl << endl; // // Z = berechne(20, 10, addiere); // cout << "Das Ergebnis der Addition ist : " << Z << endl << endl << endl; int X; X = objTest.berechne(10, 10, cTest::multipliziere); // X = objTest.berechne(10, 10,multipliziere); cout << "Das Ergebnis der Multiplikation ist : " << X << endl << endl << endl; }krieg jetzt aber leider den Fehler:
error C2039: 'waehle' : Ist kein Element von 'cTest'
ShadowEater 
-
Hi Th,
ich hab noch n bissl rumgespielt, jetzt gehts :
#include <iostream> using namespace std; class cTest { public: cTest() {} ~cTest(){} static int addiere(int a, int b) { return a + b; } static int multipliziere(int a, int b) { return a * b; } static int subtrahiere(int a, int b) { return a - b; } int berechne(int a, int b, int(*waehle)(int a, int b)) { return waehle(a, b); } }; void main() { cTest objTest; // // int Z; // int Y; // // Y = berechne(20, 10, subtrahiere); // cout << "Das Ergebnis der Subtraktion ist : " << Y << endl << endl << endl; // // Z = berechne(20, 10, addiere); // cout << "Das Ergebnis der Addition ist : " << Z << endl << endl << endl; int X; X = objTest.berechne(10, 10,cTest::multipliziere); cout << "Das Ergebnis der Multiplikation ist : " << X << endl << endl << endl; }Ich verstehe nicht so ganz warum ich nochmal explizit darauf hinweisen muss, dass multipliziere aus cTest kommt(cTest::multipliziere) ich hab doch mein Objekt objTest vom Typ cTest bekannt gemacht (cTest objTest) und berechne ist doch Memberfunktion
;Bye,
ShadowEater
!
-
In Deinem ersten Versuch hast Du falsch abgeschrieben:
(this->*waehle) // statt (*this->waehle)Im zweiten Fall erwartest Du irgendeine beliebige Funktion int(*)(int, int), die muss doch nicht automatisch in CTest liegen. Und da die statics in einer Klasse liegen musst Du sie halt qualifizieren.
-
Danke, ich glaub ich habs verstanden
!
Git static einfach an dass alle Funktionen Member sind?ShadowEater
-
Nein, Member sind sie weil sie zu einer Klasse gehören.
Static bedeutet, dass Du kein Objekt brauchst um diese Funktion aufzurufen oder anzusprechen. Du hast dann natürlich auch keinen this-Zeiger in diesen Funktionen.
Klasse::test() // funktioniert nur mit statischer Memberfunktion Klasse objekt; objekt.test() // funktioniert mit nichtstatischer Memberfunktion
-
Gut, soweit klar, könnte man sagen dass man sooft wie möglich seine Fnkt static halten sollte ?
Oder gibt es da Einschränkungen ?Bye,
ShadowEater
-
Hi ich bins nochmal
,danke Lord Jaxom umd Th
für eure Hilfe
, damit ihr seht dass es nicht vergebens war hier nochmal der Code funktionierend
:Es werden 2 ints verglichen : ist a > b ==< subtrahiere , ist a < b ==> addiere und sind se == dann multipliziere. Die Auswahl läuft über nen Funktionszeiger
Vielleicht könnt ihrs als irgendwie gebrauchen als Anschauungsmaterial oder so
:#include <iostream> using namespace std; class cTest { public: cTest() {} ~cTest(){} static int addiere(int a, int b) { return a + b; } static int multipliziere(int a, int b) { return a * b; } static int subtrahiere(int a, int b) { return a - b; } static berechne(int a, int b, int(*waehle)(int a, int b)) { return waehle(a, b); } static checkInput(int a, int b) { if ( a > b) { cout << berechne(a, b, subtrahiere)<< endl << endl; } if ( a < b) { cout << berechne(a, b, addiere)<< endl << endl << endl; } if (a == b) { cout << berechne(a, b, multipliziere)<< endl << endl; } } }; void main() { cTest objTest; objTest.checkInput(5, 5); }P.S.: Kann ich den If....... teil über ne geschickte switch Anweisung besser formulieren ?
Bye
ShadowEater
-
Hallo
static setzt du ein, wenn du es brauchst. Es gibt eine klare Abgrenzung für den Einsatz : wenn du keine andern nichtstatischen Klassenmember aufrufen must, die fragliche Methode aber logisch in den Bereich der Klasse gehört.
bis bald
akari
-
P.S.: Kann ich den If....... teil über ne geschickte switch Anweisung besser formulieren ?
Nein, ein switch geht nicht, aber du solltest "else if" verwenden, da sich die drei Anweisungen ja ausschließen
if(a > b) ... else if(a < b) ... else // a==b ...