ventajas tutorial son sintaxis que operador funciones expresiones español aprender c++ optimization c++11 lambda compiler-optimization

c++ - tutorial - operador lambda python



¿Por qué las lambdas pueden ser mejor optimizadas por el compilador que las funciones simples? (2)

La razón es que las lambdas son objetos funcionales, por lo que pasarlos a una plantilla de función creará una nueva función específicamente para ese objeto. El compilador puede trivialmente alinear la llamada lambda.

Para las funciones, por otro lado, se aplica la advertencia anterior: un puntero a la función se pasa a la plantilla de función, y los compiladores tradicionalmente tienen muchos problemas al establecer llamadas a través de punteros de función. Teóricamente pueden estar en línea, pero solo si la función circundante también está en línea.

Como ejemplo, considere la siguiente plantilla de función:

template <typename Iter, typename F> void map(Iter begin, Iter end, F f) { for (; begin != end; ++begin) *begin = f(*begin); }

Llamarlo con un lambda como este:

int a[] = { 1, 2, 3, 4 }; map(begin(a), end(a), [](int n) { return n * 2; });

Resultados en esta instanciación (creada por el compilador):

template <> void map<int*, _some_lambda_type>(int* begin, int* end, _some_lambda_type f) { for (; begin != end; ++begin) *begin = f.operator()(*begin); }

... el compilador conoce _some_lambda_type::operator () y puede realizar llamadas en línea trivialmente. (E invocar el map funciones con cualquier otra lambda crearía una nueva instanciación del map ya que cada lambda tiene un tipo distinto).

Pero cuando se llama con un puntero a la función, la instanciación se ve de la siguiente manera:

template <> void map<int*, int (*)(int)>(int* begin, int* end, int (*f)(int)) { for (; begin != end; ++begin) *begin = f(*begin); }

... y aquí f apunta a una dirección diferente para cada llamada al map y, por lo tanto, el compilador no puede hacer llamadas en línea a menos que la llamada circundante al map también esté en línea para que el compilador pueda resolver f a una función específica.

En su libro The C++ Standard Library (Second Edition) Nicolai Josuttis afirma que el compilador puede optimizar las lambdas mejor que las funciones simples.

Además, los compiladores de C ++ optimizan las lambdas mejor que las funciones comunes. (Página 213)

¿Porqué es eso?

Pensé que a la hora de crear ya no debería haber ninguna diferencia. La única razón por la que podría pensar es que los compiladores pueden tener un mejor contexto local con lambdas y pueden hacer más suposiciones y realizar más optimizaciones.


Porque cuando pasas una "función" a un algoritmo, de hecho estás pasando un puntero para que funcione, por lo que tiene que hacer una llamada indirecta a través del puntero a la función. Cuando utiliza un lambda está pasando un objeto a una instancia de plantilla especialmente instanciada para ese tipo y la llamada a la función lambda es una llamada directa, no una llamada a través de un puntero a función, por lo que es más probable que esté en línea.