10

The question is simple: what is lifetime of that functor object that is automatically generated for me by the C++ compiler when I write a lambda-expression?

I did a quick search, but couldn't find a satisfactory answer. In particular, if I pass the lambda somewhere, and it gets remembered there, and then I go out of scope, what's going to happen once my lambda is called later and tries to access my stack-allocated, but no longer alive, captured variables? Or does the compiler prevent such situation in some way? Or what?

Fyodor Soikin
  • 78,590
  • 9
  • 125
  • 172
  • I'm guessing you either get garbage or a segfualt? – the_drow Mar 05 '11 at 23:21
  • 2
    Ok, so the answer is "just don't do it"? This idea did occur to me, but... Don't do WHAT exactly? Don't remember function pointers? Or don't pass function pointers to functions? (that's the whole point, isn't it?) Or don't use lambdas at all? In other words, what is the intended use for lambdas? I mean, besides using them in calls to STL aggregate/iterate functions as is written over and over in every example. – Fyodor Soikin Mar 05 '11 at 23:25

1 Answers1

12

Depends on how you capture your variables. If you capture them by reference ([&]) and they go out of scope, the references will be invalid, just like normal references. Capture them by value ([=]) if you want to make sure they outlife their scope.

Xeo
  • 129,499
  • 52
  • 291
  • 397
  • "Depends on how you capture your variables. If you capture them by reference ([&]) and they go out of scope, the references will be invalid, just like normal references.": Why is this allowed in the first place then? – Giorgio Feb 01 '13 at 11:46
  • For when they won't go out of scope before being used. – R. Martinho Fernandes Feb 01 '13 at 12:03
  • All the same reason normal references are allowed. – Puppy Feb 01 '13 at 12:03
  • @Giorgio because what is the alternative? Making C++ a garbage-collected language? – jalf Feb 01 '13 at 12:06
  • @jalf, not, but one could forbid returning a lambda that contains captured variables by reference because this is obviously incorrect and can be detected by statical analysis. – Giorgio Feb 01 '13 at 12:19
  • @Giorgio: but you can't tell with static analysis whether the referenced variable is going to go out of scope before the lambda is used. There's nothing wrong with returning a lambda which captures a variable by reference, *as long as you ensure the referenced object's lifetime is long enough* – jalf Feb 01 '13 at 12:22
  • @jaif: If you create a lambda and return it as the result of the current method, then the captured variables go out of scope as soon as the lambda is returned, which means it will never be invoked in a valid state. Or do you get a compile error in this case? – Giorgio Feb 01 '13 at 12:26
  • @Giorgio: And what about reference-capturing variables that are *not* local to the lambda's scope? – Xeo Feb 01 '13 at 12:31
  • @Xeo: Do you mean global variables? – Giorgio Feb 02 '13 at 17:41
  • @Giorgio: No, global variables don't need to be captured. I was talking about function reference parameters, class members and nested lambdas. – Xeo Feb 03 '13 at 08:01
  • @Xeo: You're right, these must be considered too. There are probably a number of cases that cannot be covered by static analysis. It really seems a feature that is very difficult to use safely. – Giorgio Feb 03 '13 at 11:41