I have the following code:
auto get_functor = [&](const bool check) {
return [&](const foo& sr)->std::string {
if(check){
return "some string";
}
return "another string"
};
};
run(get_functor(true));
The run
function signature:
void run(std::function<std::string(const foo&)> func);
I am getting the following error which is not so clear for me:
error C2440: 'return' : cannot convert from 'main::<lambda_6dfbb1b8dd2e41e1b6346f813f9f01b5>::()::<lambda_59843813fe4576d583c9b2877d7a35a7>' to 'std::string (__cdecl *)(const foo &)'
P.S. I am on MSVS 2013
Edit:
if I edit the code by replacing auto
with the real type:
std::function<std::string(const foo&)> get_functor1 = [&](const bool check) {
return [&](const foo& sr)->std::string {
if (check) {
return "some string";
}
return "another string";
};
};
run(get_functor1(true));
I am getting another error:
error C2664: 'std::string std::_Func_class<_Ret,const foo &>::operator ()(const foo &) const' : cannot convert argument 1 from 'bool' to 'const foo &'
Which is totally messed up!
Python allows lambda nesting, i.e., you can create another lambda function inside a pre-existing lambda function. For nesting lambdas, you will need to define two lambda functions – an outer and an inner lambda function. When the outer lambda is called, the inner lambda creates a function.
No, you cannot write multiple lines lambda in Python. The lambda functions can have only one expression.
Your function can have multiple triggers. Each trigger acts as a client invoking your function independently. Each event that Lambda passes to your function has data from only one client or trigger.
As defined, a Lambda Calculus function can only take one argument. However, the effect of allowing multiple arguments to a function can be obtained using “currying”. A 2-parameter function is simulated with two 1-parameter functions. The result of applying the first function is another function.
I was able to reproduce the same error on VS 2013 with the following MVCE:
#include <iostream>
#include <functional>
#include <string>
struct foo {};
std::string run(std::function<std::string(foo const&)> f) {
return f(foo());
}
int main() {
auto get_functor = [&](bool const check) {
return [=](foo const&) -> std::string { // Line of the compiler error
if (check) {
return "CHECK!";
}
else {
return "NOT CHECK!";
}
};
};
std::cout << run(std::function<std::string(foo const&)>(get_functor(true)));
return 0;
}
I then get the error:
Error 1 error C2440: 'return' : cannot convert from 'main::<lambda_1bc0a1ec72ce6dc00f36e05599609bf6>::()::<lambda_4e0981efe0d720bad902313b44329b79>' to 'std::string (__cdecl *)(const foo &)'
The problem lies with MSVC's inability to handle returned lambdas: when you do not specify the return type, it is trying to decay it into a regular function pointer. This fails because your lambda does capture elements!
Moreover, your fix is wrong since std::function<std::string(foo const&)>
is not the type of get_functor
but rather the type you want to return from it.
Forcing the embedding into an std::function
of the returned lambda directly in get_functor
will resolve your issue:
auto get_functor = [&](bool const check) -> std::function<std::string(foo const&)> {
return [=](foo const&) -> std::string {
if (check) {
return "some string";
} else {
return "another string";
}
};
};
std::cout << run(get_functor(true));
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With