lambda this by reference

W

wo3kie

Hi,

I such example, is 'this' caught by a reference?

struct S{
void f(){
[&](){ this->i = 0;}();
}

int i;
};

I believe it is not, I think it is still caught by a value, but may you provide me some more explanation and maybe even a C++11 standard statement about this.

Thank you
Åukasz
 
V

Victor Bazarov

Hi,

I such example, is 'this' caught by a reference?

struct S{
void f(){
[&](){ this->i = 0;}();
}

int i;
};

I believe it is not, I think it is still caught by a value, but may
you provide me some more explanation and maybe even a C++11 standard
statement about this.

There is nothing in the Standard that spells out *how* 'this' is
captured. However, from the definition of 'this', you can't really
capture it by reference. Capturing by reference would enable you to
change the value, and you can't change what 'this' points to, can you?

V
 
J

James Kanze

On 6/17/2013 3:53 PM, wo3kie wrote:
I such example, is 'this' caught by a reference?
struct S{
void f(){
[&](){ this->i = 0;}();
}
int i;
};
I believe it is not, I think it is still caught by a value, but may
you provide me some more explanation and maybe even a C++11 standard
statement about this.
There is nothing in the Standard that spells out *how* 'this' is
captured. However, from the definition of 'this', you can't really
capture it by reference. Capturing by reference would enable you to
change the value, and you can't change what 'this' points to, can you?

Capture by reference wouldn't necessarily mean that you could
change it; it could be a const reference, for example. But it
would mean that you could take its address, and since "this"
doesn't have an address... (In standard terms, "this" is an
rvalue, not an lvalue.)
 
Ö

Öö Tiib

I such example, is 'this' caught by a reference?

struct S{
void f(){
[&](){ this->i = 0;}();
}

int i;
};

I believe it is not, I think it is still caught by a value, but may you provide me some
more explanation and maybe even a C++11 standard statement about this.

It is not. 'this' could make better sense as hidden reference parameter
to instance not "immutable non-null pointer". Prime reason why it is
not reference you can find in Bjarne Stroustrup's FAQ:

"Why is "this" not a reference? Because "this" was introduced into C++
(really into C with Classes) before references were added. Also, I chose
"this" to follow Simula usage, rather than the (later) Smalltalk use of
"self"." http://www.stroustrup.com/bs_faq2.html#this

Otherwise it behaves pretty much like reference.
 
W

wo3kie

Hello,

Thank you for all your replies, but I am not asking why 'this' is a pointer.. Let me state the question with another words.

[&this](){} is forbidden
[=,&this](){} is also forbidden

but

[&](){} works and catches 'this' somehow.

My question is, if in two previous examples, 'this' could not be caught by a reference, which is stated in Standard explicitly, why the third lambda works and what is about 'this' in that case?

And please, do not write everything what you know :).

Åukasz
 
V

Victor Bazarov

Hello,

Thank you for all your replies, but I am not asking why 'this' is a pointer. Let me state the question with another words.

[&this](){} is forbidden
[=,&this](){} is also forbidden

but

[&](){} works and catches 'this' somehow.

My question is, if in two previous examples, 'this' could not be caught by a reference, which is stated in Standard explicitly, why the third lambda works and what is about 'this' in that case?

And please, do not write everything what you know :).

I thought James explained it clearly enough, no? You can't capture an
rvalue by reference. Capturing by reference implies that you should be
able to get the address of the object. Since there is no object
designated by the 'this' *expression*, there can be no address of it,
hence there can be no capturing [of it] by reference.

'this' is captured either explicitly (but not when the default is '=')
or implicitly (if the lambda is inside a non-static member function).
The details are in the subclause [expr.prim.lambda], and I am not going
to quote it here - it's too long. If you'd like to see it, open the
Standard and give it a read. I don't think any of that has changed
since the release, so you can use a recent draft version.

V
 
C

Crazy Eddie

Hi,

I such example, is 'this' caught by a reference?

struct S{
void f(){
[&](){ this->i = 0;}();
}

int i;
};

I believe it is not, I think it is still caught by a value, but may
you provide me some more explanation and maybe even a C++11 standard
statement about this.

You've used a reference default, so everything you use in the body of
your lambda is captured by reference, including this.

You still can't change 'this'. It's a 'T*const'.

Also, be careful about capturing this and using default capture
clauses. Check out my blog on the matter:
http://crazycpp.wordpress.com/2011/04/06/lambda-capture-and-object-lifetime/
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,770
Messages
2,569,584
Members
45,077
Latest member
SangMoor21

Latest Threads

Top