How is it possible that this example works? It prints 6:
#include <iostream> #include <functional>  using namespace std;  void scopeIt(std::function<int()> &fun) {     int val = 6;     fun = [=](){return val;}; //<-- this }  int main() {     std::function<int()> fun;      scopeIt(fun);      cout << fun();      return 0; }   Where is the value 6 stored after scopeIt is done being called? If I replace the [=] with a [&], it prints 0 instead of 6.
It is stored within the closure, which - in your code - is then stored within std::function<int()> &fun.
A lambda generates what's equivalent to an instance of a compiler generated class.
This code:
[=](){return val;}   Generates what's effectively equivalent to this... this would be the "closure":
struct UNNAMED_TYPE {   UNNAMED_TYPE(int val) : val(val) {}   const int val;   // Above, your [=] "equals/copy" syntax means "find what variables   //           are needed by the lambda and copy them into this object"    int operator() () const { return val; }   // Above, here is the code you provided  } (val); // ^^^ note that this DECLARED type is being INSTANTIATED (constructed) too!! 
                        Lambdas in C++ are really just "anonymous" struct functors. So when you write this:
int val = 6; fun = [=](){return val;};   What the compiler is translating that into is this:
int val = 6; struct __anonymous_struct_line_8 {     int val;     __anonymous_struct_line_8(int v) : val(v) {}      int operator() () const {         return val; // returns this->val     } };  fun = __anonymous_struct_line_8(val);   Then, std::function stores that functor via type erasure.
When you use [&] instead of [=], it changes the struct to:
struct __anonymous_struct_line_8 {     int& val; // Notice this is a reference now!     ...   So now the object stores a reference to the function's val object, which becomes a dangling (invalid) reference after the function exits (and you get undefined behavior).
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