I found out that in C we can use
in lambda function []{}
Example from the article:
#include <iostream>
#include <type_traits>
int main()
{
auto funcPtr = [] {};
static_assert(std::is_same<decltype(funcPtr), void (*)()>::value);
}
The main idea of sign in lambda
You can force the compiler to generate lambda as a function pointer rather than closure by adding in front of it as above.
But what are advantages of using ' ' in lambda? Could you please provide example or link me to the explanation?
CodePudding user response:
It's not a feature of lambda and more is a feature of implicit type conversion.
What happens there is stemming from the fact that a captureless lambda can be implicitly converted to a pointer to function with same signature as lambda's operator()
. []{}
is an expression where unary
is a no-op , so the only legal result of expression is a pointer to function.
In result auto funcPtr
would be a pointer to a function, not an instance of an object with anonymous type returned by lambda expression. Not much of advantage in provided code, but it can be important in type-agnostic code, e.g. where some kind of decltype
expression is used. E.g.
#include <type_traits>
void foo(int);
template<class T>
struct is_foo : std::is_same<T, decltype(&foo)> {};
int main()
{
auto foo1 = [](int)->void {};
auto foo2 = [](int)->void {};
static_assert(is_foo<decltype(foo1)>::value, "foo1 is not like foo");
static_assert(is_foo<decltype( foo2)>::value, " foo2 is not like foo");
static_assert(is_foo<decltype(foo2)>::value, "foo2 is not like foo");
}
Note that you can do same with foo
: std::is_same<T, decltype( foo)> {};
Albeit some platforms may not support that, because they inherently may have a variety of function pointers with different calling convention and the expression will be ambiguous.
CodePudding user response:
One advantage to use function pointer against lambda in template might be to reduce the number of template instantiation.
template <typename F>
void f(F func) { func(); }
int main()
{
f([](){}); // f<lambda_1>
f([](){}); // f<lambda_2>
f( [](){}); // f<void(*)()>
f( [](){}); // f<void(*)()>
}