Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C++ lambda capture this vs capture by reference

If I need to generate a lambda that calls a member function, should I capture by reference or capture 'this'? My understanding is that '&' captures only the variables used, but 'this' captures all member variable. So better to use '&'?

class MyClass {   public:     int mFunc() {       // accesses member variables     }      std::function<int()> get() {       //return [this] () { return this->mFunc(); };       //  or       //return [&] () { return this->mFunc(); };     }    private:     // member variables } 
like image 462
vikky.rk Avatar asked Nov 06 '15 20:11

vikky.rk


People also ask

Does lambda capture reference by value?

Lambdas always capture objects, and they can do so by value or by reference.

What does it mean to lambda capture this?

The lambda is capturing an outside variable. A lambda is a syntax for creating a class. Capturing a variable means that variable is passed to the constructor for that class. A lambda can specify whether it's passed by reference or by value.

What is a lambda capture list?

The capture list defines what from the outside of the lambda should be available inside the function body and how. It can be either: a value: [x] a reference [&x] any variable currently in scope by reference [&]

Are lambdas copyable?

Copying a lambda will copy its state.


1 Answers

For the specific example you've provided, capturing by this is what you want. Conceptually, capturing this by reference doesn't make a whole lot of sense, since you can't change the value of this, you can only use it as a pointer to access members of the class or to get the address of the class instance. Inside your lambda function, if you access things which implicitly use the this pointer (e.g. you call a member function or access a member variable without explicitly using this), the compiler treats it as though you had used this anyway. You can list multiple captures too, so if you want to capture both members and local variables, you can choose independently whether to capture them by reference or by value. The following article should give you a good grounding in lambdas and captures:

https://crascit.com/2015/03/01/lambdas-for-lunch/

Also, your example uses std::function as the return type through which the lambda is passed back to the caller. Be aware that std::function isn't always as cheap as you may think, so if you are able to use a lambda directly rather than having to wrap it in a std::function, it will likely be more efficient. The following article, while not directly related to your original question, may still give you some useful material relating to lambdas and std::function (see the section An alternative way to store the function object, but the article in general may be of interest):

https://crascit.com/2015/06/03/on-leaving-scope-part-2/

like image 72
Craig Scott Avatar answered Sep 20 '22 09:09

Craig Scott