7

C++11 has both lambda's and std::function<>, but unfortunately, they have different types. One consequence is that one cannot directly use lambda's in higher order functions such as map in lisp. For example, in the following code

 #include <vector>
 #include <functional>
 using namespace std;

 template <typename A,typename B> 
 vector<B> map(std::function<B (A)> f, vector<A> arr) {
       vector<B> res;
       for (int i=0;i<arr.size();i++) res.push_back(f(arr[i]));
       return res;
}

int main () {
    vector<int> a = {1,2,3};
    map([](int x) -> int { return x;},a); //not OK

    auto id_l = [](int x) -> int { return x;};
    map(id_l,a); //not OK;

    function<int (int)> id_f = id_l;
    map(id_f,a); //OK
return 0;
}

, directly using lambda as in line 2 of main() won't work. g++ -std=c++11 testfunc.cpp returns `... testfunc.cpp:14:37: note: 'main()::__lambda0' is not derived from 'std::function'.

C++11 type inferencing fails as well, as you can see if one stores the lambda to an auto variable and then use it, the type information is still lost, probably due to type erasure and reasons of small performance penalty (as I was told: why do lambda functions in c++11 not have function<> types?).

What does work is to store the lambda in a std:function<> typed variable and use that variable. This is rather inconvenient and kind of defeats the purpose of using lambda's in functional programming in C++11. For example, one cannot manipulate lambda's in place with stuff like bind or flip, and instead has to store the lambda to a variable first.

My question is, is it possible (and how) to overcome this issue and make line#2 of main() legal, e.g. by overwriting some typecast operators? (Of course, this means I don't care about the small performance penalty involved with using/not using type erasure.)

thanks in advance.

--- EDIT ---

To clarify, the reason I use std::function rather than a generic type parameter for the functional parameter is that std::function has exact type information, while a generic type parameter as in template <typename F> map(F f, ...) contains no type information. Also, as I finally figured out, each lambda is its own type. So type erasure wasn't even a issue in the incompatibility between a lambda and its matching std::function object.

---Update---

There are already two answers about how to make the map function above work or how to improve them. Just to clarify. My question isn't about how to make map work. There are plenty of other use cases involving using the std::function<> typed parameters, which I think can at least make the code more readable and make type inferencing easy. The answers so far are about how not to use std::function<> as parameters. My question was about how to make such a function (with std::function<> typed parameters) accept lambda's automatically.

-- Update 2 ---

In response to comments, here is a example of practical case where the type information in std::function<> COULD be useful. Suppose we want to implement a C++ equivalent of fold_right : ('a -> 'b -> 'b) -> 'a list -> 'b -> 'b in OCaml (http://caml.inria.fr/pub/docs/manual-ocaml/libref/List.html).

With std::function<>, one can do

 //approach#1
 template <typename A,typename B> 
 B fold_right(std::function<B (A, B)> f, vector<A> arr, B b) {
     ...
 }

It is clear from above what f is, and what it can or cannot take. Maybe, one can also use

 //approach#2
 template <typename A,typename B, typename F> 
 auto fold_right2(F f, vector<A> arr, B b) -> decltype(f(???)) {
      ...
 }

But, this is becoming kind of ugly as you try to figure out what to put in the decltype. Also, what exactly does f take, and what's the correct way to use f? From the point view of readability, I guess the reader of the code can only figure out what is f (a function or scalar) and the signature of f by INTERPRETING the implementation in the function body.

That is what I don't like and that's where my question comes from. How to make approach#1 work conveniently. For example, if f represents addition of two numbers, approach#1 works if you create a function object first:

std::function<int (int, int)> add = [](int x, int y) -> int { return x + y; }
fold_right(add,{1,2,3},0);

Efficiency issues aside, the above code is inconvenient BECAUSE std::function cannot accept lambda's. So,

fold_right([](int x, int y) -> int { return x + y; },{1,2,3},0);

will not work currently in C++11. My question is specifically about if it is possible to make functions like fold_right defined above accept lambda's directly. Maybe it's too much to hope for. I hope this clarifies the question.

Community
  • 1
  • 1
thor
  • 21,418
  • 31
  • 87
  • 173
  • This looks like an X/Y problem. You can look [at one of my previous (albeit outdated) implementations of map if you're curious](http://stackoverflow.com/a/17755080/1381108) – Rapptz Dec 21 '13 at 19:56
  • @Yakk Yes, I realize that unfortunately, we have type-erasure, which in my opinion, cripples std::function<>. Looking at your statement the other way, if there is no good situation in which std::function could be put to good use, why does the c++11 standard bother to come up with this new feature? Is it just supposed to store callable things without any practice use? This is what my question is really about: how to or if it is possible to make it useful. – thor Jan 03 '14 at 12:14
  • @SteveJessop The effect of type inference is, of course, to infer that function `f` is unary and take a `B` and returns a `A`. This information is what the decltype approach can't provide. Restricting to vector is clearly an artifact of making an example. – thor Jan 03 '14 at 12:24
  • @SteveJessop Regarding the update, your statement seems to show that std::function<> can't be used in this single use case (without some inconvenience). There are surely other use cases, which probably both you and I agree, that std::function<> should be avoided and decltype should be used instead. My question, from the beginning, is regarding how to make std::function<> useful, not on how to use `decltype`. – thor Jan 03 '14 at 12:27
  • @TingL `std::function` lets you store callables with *type erasure*. This means doing it in a *deduced context* is not required. If you are storing a call back, if you are splitting implementation and interface -- for many reasons you use `std::function`. If you are deducing the type? Almost always a bad idea, because "type erasure" is the *opposite* of type deduction. – Yakk - Adam Nevraumont Jan 03 '14 at 12:34
  • @TingL: to paraphrase: "your statement seems to show that a screwdriver can't be used in this single use case of hammering in nails (without some inconvenience). My question is regarding how to make screwdrivers useful, not how to use hammers". The answer to how to make screwdrivers useful is: don't pick a use case that demands a hammer ;-) But if you want to pass a lambda to a function that is already defined to take a `std::function` and cannot be changed, then I think the thing to do is probably to wrap that existing function using a function template that creates the `std::function`. – Steve Jessop Jan 03 '14 at 12:38
  • ... but as far as I (or Yakk, I think) can tell, nobody should have in the first place written a function template that takes a type-deduced `function` like your `map` does. That was a bad plan from the start. – Steve Jessop Jan 03 '14 at 12:44
  • @SteveJessop I don't know why you think two different ways of defining a function screwdrivers and hammers. Also, the code works as is if you compile it. You may not like it, but it is more readable (in terms of type signature). You probably know what I mean if you compare with the C# function types. – thor Jan 03 '14 at 12:47
  • @TinL: you say the code works, but the whole point of this question is your complaint that two of your lines of code (one of which is your preferred idiom) do not compile. `std::function` can wrap a lambda, sure, there's no problem with that. But if you're only using `std::function` because you want the return type to appear as a template parameter in your function templates that take functors, then unfortunately you are in "using a screwdriver to knock in a nail" territory. – Steve Jessop Jan 03 '14 at 13:03
  • @SteveJessop You probably misunderstood my question. I have just made another update to clarify it. I am not sure about the screwdriver analogy. But the question remains. – thor Jan 03 '14 at 13:25
  • @TingL: your implementation of `fold_right` also doesn't compile when passed the name of a function `int add(int,int);`. I think you're correct that C++'s facilities for functional programming are a bit lacking, but at least for that example the use of the lambda isn't part of the problem. – Steve Jessop Jan 03 '14 at 14:56
  • "I guess the reader of the code can only figure out what is f (a function or scalar) and the signature of f by INTERPRETING the implementation in the function body" -- there is a convention to call the template parameter `BinaryFunction` rather than `F`, and some future version of C++ will include a thing called "concepts" that allows you to enforce that. It's still not everything you want, I mention it because the convention does make templates easier to read than you currently expect. You're correct that the function template signature doesn't usually include the arg type of the functor. – Steve Jessop Jan 03 '14 at 15:01
  • Lambdas in C++ are just expressions and are not the same as closures/lambdas in functional languages. Therfore you can not use lambdas in C++ in a way you would use them in OCaml or Haskel or Scheme or Lisp or ... . I repeat: Lambdas in C++ are expressions not functions. If you want that your lambdas are functions then do not C++. use Anyway, if types does not match it will fail to compile. And for your fold: Just look at std::accumulate. It is your fold based on iterators. When in Rome, do as the Romans do. – knivil Feb 10 '14 at 08:21
  • @knivil. I think the word about Rome is that anything goes in ancient Rome. I did not find your assertion that lambdas are not functions or expressions convincing. You may need to read my question to count how many times I tried to clarify this is not a question of how to write a map. Rather, it's about how to express type info. – thor Feb 11 '14 at 02:25
  • @SteveJessop I think the BinaryFunction template is obsolete. The `make_pair` wrapper here works only for lambda, a version that works for functors and function pointers is here: http://stackoverflow.com/questions/21657627/what-is-the-type-signature-of-a-c11-1y-lambda-function/21665705#21665705 – thor Feb 11 '14 at 02:29
  • I wanted to keep it short to be pertinent and keep the focus, which has been quite hard in this post. – thor Feb 11 '14 at 02:31
  • @SteveJessop I do hope concepts will make things better. They probably deprecated `BinaryFunction` and its like due to their limited expressive power compared to variadic templates. On the other hand, I don't see any problem in making `std::function` easier to use, and really don't understand the sentiments against it. – thor Feb 11 '14 at 02:42
  • @SteveJessop, I meant `make_function` wrapper two comments above. – thor Feb 11 '14 at 02:44
  • Possible duplicate: [c++ - template argument type deduction from std::function return type with lambda - Stack Overflow](https://stackoverflow.com/questions/12405102/template-argument-type-deduction-from-stdfunction-return-type-with-lambda) – user202729 Mar 21 '20 at 07:07

6 Answers6

7

Why would you want to create a dynamic indirection via std::function<...> in the first place? Just templatize on the function object and you are sorted:

template <typename A, typename F> 
auto map(F f, std::vector<A> arr) -> std::vector<decltype(f(arr[0]))> {
    std::vector<decltype(f(arr[0]))> res;
    for (int i=0; i<arr.size(); ++i)
        res.push_back(f(arr[i]));
    return res;
}

In fact, there isn't really any need for nailing the container type either and you probably want to pass it by [const] reference as well:

template <typename C, typename F> 
auto map(F f, C const& c) -> std::vector<decltype(f(*c.begin()))> {
    std::vector<decltype(f(*c.begin()))> res;
    for (auto const& value: c)
        res.push_back(f(value));
    return res;
}

Finally, please note that the standard C++ library already as a "map" function. It just happens to be spelled std::transform() and has an interface which fits the generic approach in C++ better:

std::vector<int> result;
std::transform(a.begin(), a.end(), std::back_inserter(result),
               [](int x){ return x;});
Dietmar Kühl
  • 150,225
  • 13
  • 225
  • 380
  • Maybe to minimise the interface you use, it could be `*std::begin(c)` rather than `c.front()`. This would allow containers other than sequences. I'm unsure though: the name lookup done by a range-based for loop is slightly magical and I suspect that imitating it is difficult. – Steve Jessop Dec 21 '13 at 20:06
  • @SteveJessop: I'll change the code to use a compromise: `*c.begin()` as I don't know how to do `using std::begin; *begin(c);` in a `decltype()`... – Dietmar Kühl Dec 21 '13 at 20:09
  • Thanks for your answer. std::transform() is indeed an alternative way. However, I wanted to use the function<> type because it contains complete type signature (type and parity), which can be easily used to reason about types when combined with other higher ordered functions. That's why I came up with the question and why I want to do type conversion from lambda's to std::functions<>. Both contain complete type info. The only reason I heard why lambda do not convert to std::function<> is on the basis of small performance costs. My question is how to type convert if performance is noncritical. – thor Dec 22 '13 at 01:23
  • The specific choice of std::vector is also not central to the question. It's just an example to illustrate the issue/question – thor Dec 22 '13 at 01:30
  • @TingL: You can convert from a lambda to a `std::function<...>` of known type but you can't deduce the template arguments for the `std::function<...>` from a lambda. I'm not sure if you can determine the arguments of a general lambda at all (it could be possible to capture the arguments for a lambda without any capture using a conversion to a pointer to function). In general, it is definitely impossible to determine function object argument types as these could be templated (and with C++14 lambda arguments will be allowed to be templated, too). – Dietmar Kühl Dec 22 '13 at 01:34
  • @DietmarKühl. Yes. I think template arguments of std::function<> can be used in type inferencing, and those of lambda's cannot probably because of type erasure. What I attempted to do is to convert lambda's to std::function<>'s, so that they can be used in type deduction after the conversion. Since we can do `std::function<...> f = some lambda`, I was asking if the conversion here can be made automatic so that the `map` function in the example can accept lambda's. :) – thor Dec 22 '13 at 01:44
  • 1
    @TingL: I understand what you try to do (deduce the argument types of a lambda expression) and as stated above I don't think it is possible in general. For the specific case you have above, it should be possible by jumping through a function which takes a function point but as soon as the lambda has a capture that won't be possible. – Dietmar Kühl Dec 22 '13 at 01:52
  • @DietmarKühl Thanks. I had this feeling that lambda argument types cannot be type inferenced. What I was looking for is not to directly deduce lambda argument types, but convert lambda's to std::function<>'s automatically/implicitly. I start to feel as if the std::function<> or lambda is defective here, because whenever I ask how to make it useful, the answers I got (correctly) are that, no, you shouldn't be using std::function<>. Other pre-existing language features allow you to do it. – thor Dec 22 '13 at 02:20
  • 1
    @Dietmar: "I'm not sure if you can determine the arguments of a general lambda at all" certainly you won't be able to once generic lambdas arrive, because such lambdas *do not have* parameter types :-) – Steve Jessop Jan 03 '14 at 13:07
6

Your map function is broken. Do not use std::function unless you cannot use a template; and in this instance, you most assuredly can. You don't need B as a template parameter because decltype can give it to you, and you don't need the argument type to actually be a std::function at all.

template <typename A, typename F> auto map(F f, vector<A> arr) -> std::vector<decltype(f(arr.front())> {
    std::vector<decltype(f(arr.front())> res;
    for (int i=0;i<arr.size();i++) res.push_back(f(arr[i]));
    return res;
}

For the record, this is ignoring everything else wrong with your map function.

Puppy
  • 144,682
  • 38
  • 256
  • 465
  • No, my map function is not broken, if you use line#6 and 7 in the main function. The other two use cases are what I intend to make working. I am ware of your method, which basically says F can be any type and relies on caller to provide the correct type for F. There is no type inference or safety at all. So, you method works perfectly fine. But it is not related to my question, which is about fixing the link between lambda and std::function<>. – thor Dec 22 '13 at 01:26
  • 1
    @TingL No type inference? "Broken" is a bit strong but it's not generic enough to work with your desired set of argument types. The solution is to be more generic, which this answer demonstrates. You should probably also get rid of the explicit specification of `std::vector`. – Potatoswatter Dec 22 '13 at 01:45
  • Please see the update. The solution in the answer is probably more generic. But it does not address the question itself. The use of vector<> is just to illustrate the question. I don't think the example is the best way to write a `map` function. But it did work and served to illustrate the question. Telling me how to write it a different way to circumvent the question does not answer it. I surely know there are other ways to write `map`'s. – thor Dec 22 '13 at 01:51
6

Finally figured out a generic wrapper function make_function (in current c++11) for converting any lambda to its corresponding std::function object with type deduction. Now instead of using ctor:

map(function<int (int)>( [](int x) -> int { return x;} ), {1,2,3});

which requires giving the same type information twice, the following succinct form works

map(make_function([](int x) -> int { return x;}),a); //now OK

Code is below:

 #include <vector>
 #include <functional>
 using namespace std;

 template <typename T>
 struct function_traits
    : public function_traits<decltype(&T::operator())>
 {};

 template <typename ClassType, typename ReturnType, typename... Args>
 struct function_traits<ReturnType(ClassType::*)(Args...) const> {
    typedef function<ReturnType (Args...)> f_type;
 };

 template <typename L> 
 typename function_traits<L>::f_type make_function(L l){
   return (typename function_traits<L>::f_type)(l);
 }

 template <typename A,typename B> 
 vector<B> map(std::function<B (A)> f, vector<A> arr) {
       vector<B> res;
       for (int i=0;i<arr.size();i++) res.push_back(f(arr[i]));
       return res;
}

int main () {
    vector<int> a = {1,2,3};
    map(make_function([](int x) -> int { return x;}),a); //now OK
    return 0;
}

--original answer--

To answer my own question after a couple of weeks' search (and getting chastised for using std::function<> as parameters), probably the best way I can find to have function<>-typed parameters accept lambda's (in c++11) is simply via explicit cast:

map((function<int (int)>) ([](int x) -> int { return x;} ), {1,2,3});

Or using ctor:

map(function<int (int)>( [](int x) -> int { return x;} ), {1,2,3});

For comparison, if you have a function taking std::string (e.g. void ff(string s) {...}), it can take const char* automatically. (ff("Hi") would work). The automatic conversion from lambda to std::function<> does not similarly work in c++11 (, which is unfortunate, IMO).

Hopefully, things will improve in c++14/1y when lambdas can be properly typed or better type-deduced.

thor
  • 21,418
  • 31
  • 87
  • 173
  • The specifications of lambdas, `std::function`, conversion, and deduction are unlikely to change. You simply implemented my `dynamic_function_from_lambda` suggestion, except doing the work manually instead of making a generic function. – Potatoswatter Jan 09 '14 at 00:03
  • @Potatoswatter Yes, you can view the std::function<> ctor as a function. In that sense, the type conversion operator I mentioned is also a function. Your suggestion did not add much to that. Mine answer does not add much either, except that my answer shows that the std::function ctor suffices, and there is no need to write such a function. – thor Jan 09 '14 at 02:48
  • @The true answer I was looking for, as evident in the title of the original question, is to find a way to eliminate the explicit type conversion. In that sense, most answers including yours suggested using something else such as `decltype` or `result_of` to replace what `std::function` does in my question. – thor Jan 09 '14 at 02:50
  • `decltype` and `result_of` are perfectly fine, and probably more efficient. But there are apparently a different way of programming (for type deduction) than simple deduction using the explicit type parameters in std::function<>. That's why I think the rest of your answer (except that type conversion can be a function) does not apply to the question directly. – thor Jan 09 '14 at 02:57
  • Just in reply to the first comment here, a `dynamic_function_from_lambda` function is different from a `function` constructor in that it can perform deduction and avoid the explicit `` as in your code. – Potatoswatter Jan 10 '14 at 01:42
  • @Potatoswatter If that is the case, then in what sense did my answer here using `function` ctor simply implement your `dynamic_function_from_lambda` suggestion? Look, I don't think there is much point in figuring our if my answer simply implements your `dynamic_function_from_lambda` suggestion, or if that suggestion simply paraphrases the question itself. I did not accept my own answer even though I believe it's the closest because neither my answer nor yours completely solved the problem. I put up an answer here just because it's a practical work-around that I found useful. – thor Jan 10 '14 at 20:27
  • Your original reason for wanting to use `std::function`: _"it has exact type information, while a generic type parameter as in `template map(F f, ...)` contains no type information"_. But as your answer demonstrates, it is quite easy to use type traits to extract type information from a lambda or other callable object. – Oktalist Apr 09 '14 at 15:29
  • Yes, I was finally able to do that, and it wasn't difficult hind-sight. Not easy or obvious the first time round as you can read from the answers/comments. – thor Apr 10 '14 at 02:02
3

My question was about how to make such a function (with std::function<> typed parameters) accept lambda's automatically.

You can't. Why do you suppose this is possible? std::function is part of the standard library, and it has no capabilities beyond what is possible with other class types.

Moreover, by artificially restricting the solution space to function calls with a lambda as the argument and a std::function<T> as the parameter with deduced T, there is nothing to possibly change. The argument will not match the parameter, and you've arbitrarily decided to forbid changing either.

Given a function dynamic_function_from_lambda to encapsulate any lambda in a std::function, you could perform the conversion explicitly either in the function call or the body of a function accepting lambda objects by deduction.

Alternative A:

map( dynamic_function_from_lambda( []( int a ){ return a + 1 } ), v );

Alternative B:

template< typename F, typename V >
std::vector< typename std::result_of< F( typename V::value_type ) >::type >
map( F f, V v )
    { return map( dynamic_function_from_lambda( f ), std::move( v ) ); }

The whole point of std::function is runtime polymorphism though, so if you're not using that, it is just wastefully inefficient.

Potatoswatter
  • 134,909
  • 25
  • 265
  • 421
  • You are missing the point. 1) `std::string` can take `const char *` automatically with type conversion. That's why you can declare a function `f(string s,...)` and called it with `f("Hi",...)`. There is nothing impossible here. – thor Jan 08 '14 at 14:00
  • 2) I don't see how your answer helps in achieving the same thing for std::function<> like the std::string case above. – thor Jan 08 '14 at 14:08
  • @TingL By design, the language will not perform conversion and deduction simultaneously. You can convert a lambda to a given concrete `std::function` type, but you cannot convert a lambda, or anything else, to `template std::function`. – Potatoswatter Jan 08 '14 at 23:54
  • Frankly, I see no strong reason why a lambda cannot auto-convert to std::function as a const char* can convert to std::string. Probably this is more by accident than by design, as I don't see a good reason to forbid this conversion. I only arguments I heard so far is that there is type erasure and lambda's do not support templates. None of these are core to the concept of C++. I heard that lambda is going to support templates in C++14. – thor Jan 09 '14 at 03:04
  • Regarding c++ not performing conversion and deduction simultaneously, I can see currently many things involving templates are not supported. `typedef`'s did not support templates so they came up with `using`. Is there a fundamental reason why new features cannot be added to allow conversion operators with templates? – thor Jan 09 '14 at 03:15
  • @TingL `std::string` is not a template as `std::function` is. It's a *specialization* of `std::basic_string`, but a generic `std::basic_string` parameter cannot accept a `char *` for exactly the same reason as your issue. Conversion and deduction can't be done simultaneously because it would incur a combinatorial complexity explosion, and you can already code around as necessary using more advanced techniques as I point out in this answer. – Potatoswatter Jan 10 '14 at 01:39
  • Thanks for pointing out the complexity issue here. I appreciate your answer, but don't agree 'The whole point of std::function ... so if you're not using that, it is just wastefully inefficient.' And your answer suggests falling back to using older c++ template programming, which is clearly not what my question is asking. The question clearly asks about how `function` can be used other than merely for storage. Therefore, it would be misleading to accept your answer, suggesting that your answer solved the problem in any way. You'll probably see if you apply your answer to the original examples. – thor Jan 10 '14 at 20:36
  • You did not solve the question, but altered it. Your answer is the status quo and standard practice now. I picked up template programming a couple of years ago myself, and I am still using it. What I don't like about `decltype` and `result_of` is the extra programming (probably in the pre-compilation phase) just to figure out the types, which in most cases should be known before you start the template programming. Having said that, I believe that your question and my question are talking about different approaches. – thor Jan 10 '14 at 20:50
0

Actually you could do it and even better (faster, cheaper) than with std::function. It has a heap alloc and a virtual function call. Its needed only for type erasure (to accept ANY CALLABLE with same signature). But for lambdas you don't need this (costly) flexibility. Just use lambda wrapper class

#include <iostream>
#include <functional>
#include <vector>

template <typename T, typename ... Args>
struct lambda_wrapper : public lambda_wrapper<decltype(&T::operator())(Args...)> {
    using RetType = decltype(&T::operator())(Args...);
};

template <typename L>
struct lambda_wrapper<L> {
private:
    L lambda;

public:
    lambda_wrapper(const L & obj) : lambda(obj) {}

    template<typename... Args>
    typename std::result_of<L(Args...)>::type operator()(Args... a) {
        return this->lambda.operator()(std::forward<Args>(a)...);
    }

    template<typename... Args> typename
    std::result_of<const L(Args...)>::type operator()(Args... a) const {
        return this->lambda.operator()(std::forward<Args>(a)...);
    }
};
template <typename T>
auto make_lambda_wrapper(T&&t) {
    return lambda_wrapper<T>(std::forward<T>(t));
}

template <typename A, typename F>
auto map(F f, std::vector<A> arr)
{
    std::vector < decltype(f(arr.front())) > res;
    for (int i=0;i<arr.size();i++) res.push_back(f(arr[i]));
    return res;
}

int main(int argc, char ** argv) {

    std::vector<int> a = {1,2,3};

    map(make_lambda_wrapper([](int a) -> int { return a*2;} ),a);

}
barney
  • 2,172
  • 1
  • 16
  • 25
0

You can use &LambdaT::operator() to get lambda args as the following:

template <typename R, typename LambdaT, typename... Args>
auto _LambdaToStdFunction(LambdaT lambda, R (LambdaT::*)(Args...) const) {
  return std::function<R(Args...)>(lambda);
}
template <typename LambdaT>
auto LambdaToStdFunction(LambdaT &&lambda) {
  return _LambdaToStdFunction(std::forward<LambdaT>(lambda),
                              &LambdaT::operator());
}

Note: constant qualifier

Test example ideone:

#include <functional>
#include <iostream>
#include <vector>

template <typename LambdaT, typename R, typename... Args>
auto _LambdaToStdFunction(LambdaT lambda, R (LambdaT::*)(Args...) const) {
  return std::function<R(Args...)>(lambda);
}
template <typename LambdaT>
auto LambdaToStdFunction(LambdaT &&lambda) {
  return _LambdaToStdFunction(std::forward<LambdaT>(lambda),
                              &LambdaT::operator());
}

template <typename A, typename B>
std::vector<B> map(std::function<B(A)> f, std::vector<A> arr) {
  std::vector<B> res;
  for (int i = 0; i < arr.size(); i++) res.push_back(f(arr[i]));
  return res;
}

int main() {
  std::vector<int> a = {1, 2, 3};
  auto f = LambdaToStdFunction([](int x) -> int {
    std::cout << x << std::endl;
    return x;
  });
  map(LambdaToStdFunction([](int x) -> int {
        std::cout << x << std::endl;
        return x;
      }),
      a);  // now OK
  return 0;
}
I.Omar
  • 501
  • 7
  • 19