C ++ Lambda hat keinen Operator ()

8

Ich brauche eine Methode, um die Argumenttypen einer Funktion herauszufinden, und so schrieb ich eine closure_traits-Klasse, wie unten angegeben, inspiriert von Ist es möglich, den Parametertyp und den Rückgabetyp eines Lambdas herauszufinden? .

Wenn ich jedoch versuche, es auf ein einfaches Lambda anzuwenden, bekomme ich den Fehler, dass 'operator ()' kein Mitglied von '(Lambda-Typ)' ist. Laut cppreference haben Lambdas jedoch einen Operator (). Ich versuchte auch, std :: function zu verwenden, und erhielt den äquivalenten Fehler. Ich schätze, ich bin mir nicht sicher, was schief läuft, und jede Hilfe würde sehr geschätzt werden.

%Vor%

Die Compiler-Fehlermeldungen, die ich bekomme, sind unten. Mein Kompilierbefehl ist einfach g ++ -std = c ++ 14 main.cpp.

%Vor%     
sangrey 03.11.2016, 21:06
quelle

3 Antworten

9

Ihre Spezialisierung stimmt nicht mit dem Argument decltype(&T::operator()) überein.

Aus diesem Grund muss der Compiler, anstatt die Spezialisierung (wie gewünscht) auszuwählen, rekursiv dieselbe Hauptvorlage auswählen. Dadurch wird &T::operator() expression erneut angewendet, nachdem es bereits einmal angewendet wurde. Der erste Versuch, &T::operator() zu machen, ist tatsächlich erfolgreich, aber dann versucht der Compiler &T::operator() erneut anzuwenden, wenn T bereits int (main()::<lambda(int)>::*)(int) const ist. Letzteres hat offensichtlich nicht operator () , weshalb Sie diese Fehlermeldung erhalten.

Der Grund, warum Sie Ihre Spezialisierung nicht auswählen können, ist das Fehlen von const in der Template-Parameter-Deklaration. Das Lambda operator () ist eigentlich ein const Mitglied der Lambda Klasse. Fügen Sie const zur Deklaration Ihrer Spezialisierung hinzu

%Vor%

und der Compiler folgt dem Spezialisierungspfad, dem Sie folgen wollen.

Und natürlich müssen Sie closure_traits<decltype(thing)>::arity::value drucken, nicht nur closure_traits<decltype(thing)>::arity .

    
AnT 03.11.2016, 21:16
quelle
4

Der Compiler erhält korrekt den operator() des Lambdatyps, aber ein Zeiger auf diese Memberfunktion stimmt aufgrund des const -Qualifikators nicht mit Ihrer Spezialisierung überein.

Sie sollten eine zweite Spezialisierung hinzufügen

%Vor%

(Ja, das Schreiben von Vorlagen für einen Funktionstyp ist schmerzhaft.)

    
aschepler 03.11.2016 21:17
quelle
1

Falls jemand Probleme damit hat, ist der korrekte Code wie folgt:

%Vor%     
the4thamigo_uk 08.01.2018 21:21
quelle