sie entfernen den syntaktischen Zucker, dass die Lambda-Funktionen uns zur Verfügung stellen zu tun:
struct lambda1 {
void operator() {
std::cout << "Lambda 1!" << std::endl;
}
};
struct lambda2 {
void operator() {
std::cout << "Lambda 2!" << std::endl;
}
};
int main(int argc, char *argv[]) {
auto l1 = Lambda1{};
auto l2 = Lambda2{};
auto l1p = &l1; // l1p is a Lambda1 *
l1p = &l2; // &l2 is a Lambda2 *
return 0;
}
Dies ist nicht die genaue Transformation vom Compiler getan, aber ich denke, es reicht aus, um das Problem zu untersuchen:
Die beiden Lambdas haben jeweils einen eigenen Typ, der völlig unabhängig von ihren Argumenten, erfassten Variablen oder dem Rückgabetyp ist. Und natürlich sind die Arten von Lambdas zueinander nicht verwandt, so dass Sie offensichtlich keinen Zeiger auf einen von der Adresse des anderen zuweisen können.
Die Lösung in der anderen Antwort mit dem Funktionszeiger ist ziemlich nett. Gäbe es keine „nur dafür bezahlen, wenn Sie es verwenden“ Lehre für C++, haben wir Lambda-Funktionen wie
struct SomeLambda
: public LambdaBase<
Capture<int>,
Arguments<bool>,
Return<void>> {
// ...
};
/*
[integer]
(bool flag) {
if (flag) cout << integer;
}
*/
Aber für das Sinn der Basis machen machen können müsste polymorph sein (hat eine virtuelle Mitgliederfunktion), und das sind Kosten, die Sie nicht brauchen, wenn Sie nicht beabsichtigen, das zu tun, was Sie wollten.
In C++ 11 (+) Ich würde es vorziehen 'std zu verwenden :: Funktion l1f = l1; l1f = l2; 'genauso wie es einfacher zu lesen ist. –
@SimonKraemer * bitte * nicht. Der Overhead von 'std :: function' ist die geringfügige syntaktische Verbesserung nicht wert. Benutze einfach 'typedef'. – Quentin
@Quentin Ich habe gerade die Compiler-Ausgabe überprüft. Ich bin wirklich überrascht über den massiven Overhead. Danke, dass du es aufgezeigt hast. –