How to declare a function vector (lambda)

I saw how to declare a vector of functions (see calling a function from a vector ).

But that answers user pointers. How to create a vector of / lambdas functions using the new syntax in modern C ++?

Examples of functions using the new syntax usually use auto:

auto f = [] (std::string msg) -> void { std::cout << msg << std::endl; }; 

What is the actual type f? so can i declare a vector of this type?

Thanks so much for any help

+5
source share
3 answers

Use std::function with the appropriate type:

 std::vector<std::function<void(void)>> vec; vec.push_back([]()->void{}); 

In your case, it will be std::function<void(std::string)> .

The exact type of lambda does not make sense for the standard one ([expr.prim.lambda] / 3):

The type of lambda expression (which is also the type of a closure object) is a unique, unnamed type of non-unit class

+11
source

What is the actual type f ? so can i declare a vector of this type?

Type f can only be inferred using auto . You can declare a vector this type using

 std::vector<decltype(f)> v; 

However, this is not very useful. Lambda functions that seem strikingly similar have different types. Even worse, lambda functions having the same body also have different types.

 auto f = [] (std::string msg) -> void { std::cout << msg << std::endl; }; auto g = [] (std::string msg) -> void { std::cout << msg << std::endl; }; auto h = [] (std::string msg) -> void { std::cout << msg << '+' << msg << std::endl; }; 

Given the above functions, you cannot use

 std::vector<decltype(f)> v; v.push_back(f); // OK v.push_back(g); // Not OK v.push_back(h); // Not OK 

Your best option is to create std::vector from std::function s. You can add lambda functions to this std::vector . Given the above definitions of f and g , you can use:

 std::vector<std::function<void(std::string)>> v; v.push_back(f); v.push_back(g); v.push_back(h); 
+7
source

As mentioned, each lambda you declare has a unique context-specific type, even if it has an apparently identical signature. That's why the lambda vector has only theoretical significance - you could push no more than one lambda there ... You have two options: you can agree with the proposed approach from other answers and store lambdas in the erase type std::function before put them in a vector or put your lambdas in a "container", which will collect the type of each element separately from the lambda object itself - std::tuple :

 auto t = std::make_tuple([](){ std::cout<<"First lambda" << std::endl; }, [](){ std::cout<<"Second lambda"<< std::endl; }, [](){ std::cout<<"Third lambda" << std::endl; }); 

and get the corresponding lambda at compile time:

 std::get<0>(t)(); // the value in get must be known at compile time! // otherwise compiler won't be able to establish type // of lambda and the whole point of using tuple is lost 

[live demo]

0
source

Source: https://habr.com/ru/post/1260121/


All Articles