Normalerweise verwende ich das folgende Muster, wenn ich ein Lambda als Argument für eine Funktion akzeptiere (Eine Template-Klasse, die als Wert übergeben wurde):
%Vor%Ist diese Kopie (das Schließen) des Arguments? Wenn ja, ist es falsch, stattdessen das Lambda durch const-Referenz zu akzeptieren?
%Vor%Ein einfacher Test scheint darauf hinzuweisen, dass dies gut funktioniert, aber ich möchte wissen, ob es spezielle Überlegungen gibt, die ich beachten sollte.
Wenn Sie den Wert übergeben, kopieren Sie das Closure-Objekt (vorausgesetzt, Sie definieren das Lambda nicht inline, in diesem Fall wird es verschoben). Dies kann unerwünscht sein, wenn der Zustand teuer zu kopieren ist, und wird nicht kompiliert, wenn der Status nicht kopierbar ist.
%Vor% Wenn Sie an const
reference übergeben, können Sie kein mutable
lambda übergeben, das seine Datenelemente als Argument für higherOrderFunction()
ändert, weil ein mutable
lambda ein nicht const
operator()
hat. und Sie können das nicht auf einem const
-Objekt aufrufen.
Am besten verwenden Sie eine Weiterleitungsreferenz. Dann kann higherOrderFunction
entweder lvalues oder rvalues akzeptieren, die der Aufrufer übergibt.
Dies ermöglicht sowohl die einfachen Fälle als auch die oben genannten zu kompilieren. Eine Erläuterung, warum std::forward
verwendet werden sollte, finden Sie unter diese Antwort .
Eine Kopie ist eine Kopie, so dass Sie das Original nicht mutieren können. Dies kann Auswirkungen auf die Leistung haben, wenn viele Daten beteiligt sind:
%Vor%Sehen Sie in Aktion .
Nicht vergessen: Lambdas sind nur syntaktischer Zucker für aufrufbare Klassen. (Aber sehr hilfreich)
Tags und Links c++ lambda c++11 closures pass-by-reference