¿Cuál es la forma correcta de definir una función que recibe un int->intparámetro lambda por referencia?
void f(std::function< int(int) >& lambda);
o
void f(auto& lambda);
No estoy seguro de que la última forma sea incluso sintaxis legal.
¿Hay otras formas de definir un parámetro lambda?

const&?Respuestas:
No puede tener un
autoparámetro. Básicamente tienes dos opciones:Opción # 1: Úselo
std::functioncomo lo ha mostrado.Opción # 2: Use un parámetro de plantilla:
template<typename F> void f(F &lambda) { /* ... */}La opción n. ° 2 puede, en algunos casos, ser más eficiente, ya que puede evitar una posible asignación de montón para el objeto de función lambda incrustado, pero solo es posible si
fse puede colocar en un encabezado como una función de plantilla. También puede aumentar los tiempos de compilación y la huella de I-cache, al igual que cualquier plantilla. Tenga en cuenta que también puede no tener ningún efecto, ya que si el objeto de la función lambda es lo suficientemente pequeño, puede representarse en línea en elstd::functionobjeto.fuente
std::functionprimero a través del contenedor de propósito general )std::functionobjeto" es engañosa. Las lambdas siempre están disponibles en línea (el compilador puede optar por no hacerlo, por supuesto).std::functionLas implementaciones generalmente usan optimización de objetos pequeños para evitar asignaciones de montón. Si una lambda tiene una lista de captura lo suficientemente pequeña , se almacenarástd::functionsin usar el montón. Aparte de eso, el tamaño de una lambda no tiene ningún significado real.&dentrovoid f(F & lambda)?Yo usaría
templatecomo:template<typename Functor> void f(Functor functor) { cout << functor(10) << endl; } int g(int x) { return x * x; } int main() { auto lambda = [] (int x) { cout << x * 50 << endl; return x * 100; }; f(lambda); //pass lambda f(g); //pass function }Salida:
500 1000 100Demostración: http://www.ideone.com/EayVq
fuente
Sé que han pasado 7 años, pero aquí hay una forma en que nadie más mencionó:
void foo(void (*f)(int)){ std::cout<<"foo"<<std::endl; f(1); // calls lambda which takes an int and returns void } int main(){ foo([](int a){std::cout<<"lambda "<<a<<std::endl;}); }Qué salidas:
foo lambda 1No se necesitan plantillas o std :: function
fuente
std::functioncaso) mientras que la versión con plantilla no tiene esta limitación.Eso está cerca. Lo que realmente compilará es:
#include <cassert> /*constexpr optional*/ const auto f = [](auto &&lambda) { lambda(); lambda(); }; int main() { int counter = 0; f([&]{ ++counter; }); assert(counter == 2); }fuente