for_each
-
Hallo,
Ich habe in meiner Klasse Worker eine map<string, Work> workers und damit der Benutzer von Worker irgend eine Operation auf alle Elemente Work der Map aufrufen kann, hab ich ihr eine forEach Methode spendiert:
template <typename UnaryFunction> void Worker::forEachWork(UnaryFunction fn) { for(WorkMap::iterator it = workers.begin(); it != workers.end(); ++it) fn(it->second); }1. Frage: Ist das eine gute Idee? Oder sollte ich lieber einen Iterator auf die map liefern?
2. Ich habe Probleme mit dem Aufruf. Meine Unaryfunction ist eine STATISCHE Methode, die so aussieht:
void EditorForm::setWorkInactive(Work* rt) { rt->setActive(false); } // Aufruf: worker->forEachWork(EditorForm::setWorkInactive);Das kompilert auch, nur kriege ich einen Linkerfehler (die Fehlermeldung is elendig lange und möchte ich euch ersparen).
Weiß wer wieso das nicht geht? Und wie es geht?
-
Das kompilert auch, nur kriege ich einen Linkerfehler (die Fehlermeldung is elendig lange und möchte ich euch ersparen).
mach mal trotzdem, wenn man sich die meldung anguckt, sieht man, was falsch läuft - so seh ich auf einen blick nichts falsches...
bb
-
Also, ich hab den Code jetzt geändert. Meine Unary function ist jetzt eine freie Funktion (sie macht in der Klasse EditorForm keinen Sinn):
void setWorkInactive(Work* w) { w->setActive(false); } // Aufruf: worker->forEachWork(setWorkInactive);Kompiliert einwandfrei, nur gibt wieder einen Linkerfehler. Den Linkerfehler möchte ich erstmal nicht posten (ist ein Firmenprojekt und da sollte ich eigentlich keine Namen posten. Meine Typnamen habe ich für diesen Thread alle umbenannt).
Aber vielleicht weiß ja wer auch ohne Linkererror, wieso das nicht klappt?
Ich hab setWorkInactive grade probiert mit std::for_each, und da klappt alles (kein Linkerfehler!) Wieso geht es bei meinem forEachWork nicht?
-
Ich glaube ich konnte den Fehler eingrenzen. Ich glaube meine Template Methode forEachWork() ist falsch. Es ist eine Template Methode in einer NICHT-Template Klasse:
// .h class Work { template <class UnaryFunction> void forEachWork(); }; //.cpp template <class UnaryFunction> void Work::forEachWork() { }Das stimmt nicht ganz, oder? Ich habs auch mit template <class UnaryFunction>
void Work<UnaryFunction>::forEachWork() probiert, aber das gibt einen Compilerfehler. Ist meine Methode falsch definiert? Falls ja: Wie gehts richtig?
-
frager+ schrieb:
// .h class Work { template <class UnaryFunction> void forEachWork(); }; //.cpp template <class UnaryFunction> void Work::forEachWork() { }Das stimmt nicht ganz, oder?
Richtig erkannt. Da die Definition des Funktions-Templates nur in der cpp-Datei steht, Du sie aber anderswo mit einem bestimmten UnaryFunction-Typ benutzen willst, kann der Compiler diese Funktion nicht erzeugen. Das, was in der cpp-Datei steht ist quasi nur eine Bauanleitung für die Funktion. Wenn Du die cpp-Datei kompilierst, erzeugt der Compiler keine forEachWork-Funktion.
Du kannst das Problem beheben, indem Du die Definition der Elementfunktion in die Header-Datei verlagerst.
Gruß,
SP
-
Danke Sebastian
