c++11 - Function taking lambda expression -


for practicing purposes wanted create function similar std::transform():

template<class tin, class tout> std::vector<tout> map( const std::vector<tin>& in,                        const std::function<tout(const tin&)>& mapper ) {     std::vector<tout> ret;    for( auto elem : in ) {        ret.push_back( mapper( in ) );    }     return ret; } 

and intended use follows:

std::vector<bar> bars /* = ... */; std::vector<foo> foos = map( bars, []( const bar& bar ) { return bar.to_foo(); } ); 

however, undefined references function call. correct signature map() function?

*update: * here's actual error message (bar = std::string, foo = ipv6 (own class))

config.cc:98:61: error: no matching function call ‘map(const std::vector<ipv6>&, interfaceconfig::set_ip6(const std::vector<ipv6>&)::<lambda(const ipv6&)>)’ config.cc:98:61: note: candidate is: utils.h:38:31: note: template<class tin, class tout> std::vector<tout> utils::map(const std::vector<tin>&, const std::function<tout(const tin&)>&) 

and here's call: std::vector strings = utils::map( ips, []( const ipv6& ip ) { return ip.to_string(); } );

there 2 things in code not work.

  • first, when passing lambda function argument, suggest using template. standard library on microsoft seems use method std::for_each example.
  • and :

    when function template has return type, cannot deduced arguments, or when function template doesn't have argument, type cannot deduced compiler. function require template type argument specification.

take @ example :

template<class tout, class tin, class fun> //                            ^^^^^^^^^^^ // note changed order of types std::vector<tout> map( const std::vector<tin>& in,                        fun mapper ) { //                     ^^^^^^^^^^    std::vector<tout> ret;    for( auto elem : in ) {        ret.push_back( mapper( elem ) );    }     return ret; }  int main() {     std::vector<int> bars /* = ... */;     std::vector<float> foos = map<float>( bars, []( int ) { return 1.0f; } );     //                           ^^^^^^^ specify type tout     system( "pause" );     return 0; } 

edit :

like said in comment, can use decltype , std::decay not have explicitly specify result of function :

  template<class tin, class fun> // no tout //                  ^^^^^^^^^^^   auto map( const std::vector<tin>& in, fun mapper ) //^^^^                                  ^^^^^^^^^^     -> std::vector<typename std::decay< decltype( mapper( in.front() ) )>::type > {     std::vector<typename std::decay< decltype( mapper( in.front() ) )>::type > ret;      for( auto elem : in ) {        ret.push_back( mapper( elem ) );    }     return ret; }  int main() {     std::vector<int> bars /* = ... */;     std::vector<float> foos = map( bars, []( int ) { return 1.0f; } );     //                           no specification     system( "pause" );     return 0; } 

let's explain little bit.

first use late-specified return type syntax. allow use parameter names in return type specification. start line auto , put return type specification after parameters using ->.

we use decltype because decltype type specifier yields type of specified expression. useful in our case. example type of function passed in parameters, decltype( f( somearg ) ).

let's state want : return type of function should vector of return type of function passed in argument right ? can return std::vector< decltype( mapper( in.front() ) )> , that's ! (why in.front() ? have pass parameter function have valid expression.)

but here again, have problem : std::vector not allow references. not problem us, use std::decay meta-function applies lvalue-to-rvalue, array-to-pointer, , function-to-pointer implicit conversions type t, removes cv-qualifiers, remove references, , defines resulting type member typedef type.. is, if function returns const foo& end in foo.

the result of of : std::vector< typename std::decay< decltype( mapper( in.front() ) )>::type >.

you have repeat expression again @ beginning of function declare variable return.

some usefull references :

it not easy explain, hope explanations understandable.


Comments

Popular posts from this blog

php - Calling a template part from a post -

Firefox SVG shape not printing when it has stroke -

How to mention the localhost in android -