views:

162

answers:

4

On this page, it's written that

One reason is that the operand of delete need not be an lvalue. Consider:

delete p+1; 
delete f(x); 

Here, the implementation of delete does not have a pointer to which it can assign zero.

Adding a number to a pointer shifts it forward in memory by those many number of sizeof(*p) units.

So, what is the difference between delete p and delete p+1, and why would making the pointer 0 only be a problem with delete p+1?

A: 

The reason is that neither of those are lvalues so setting them to NULL (or any other value) is simply not possible.

Andrew Medico
Steve Jessop
+5  A: 

p and p+1 point to different places, as you rightly said sizeof(*p) units apart. You can't delete something that hasn't been allocated, but for example:

A* p = new A();
p++;
delete p-1;

would delete the original allocation. Deleting p+1 when p+1 wasn't allocated originally is undefined; glib flips out with:

*** glibc detected *** free(): invalid pointer: 0x0804b009 ***

The implementation can't zero p+1 because p+1 isn't a variable to modify. The paragraph was saying that

delete p;

could be translated to

free(p);
p = 0;

That doesn't make sense with p+1

Michael Mrozek
The first part of your answer is irrelevant - this has nothing to do with whether 'p+1' is a valid pointer. The point is that it's not an lvalue.
Andrew Medico
What? He asked two things, the first was "what is the difference between delete p and delete p+1"
Michael Mrozek
@Andrew Medico: is it not an `lvalue` because we did not allocate memory for it using `new()`, or for some completely different reason?
Lazer
@eSKay They're unrelated. lvalues are values that have an address, and can therefore appear on the left side of an equation. `p` has an address, as it's a variable. `p+1` doesn't; the value `p` points to is summed with 1 and that temporary is used inline, but it isn't stored permanently in memory somewhere
Michael Mrozek
+7  A: 

You can't do p + 1 = 0. For the same reason, if you do delete p + 1 then delete cannot zero out its operand (p+1), which is what the question on Stroustrup's FAQ is about.

The likelihood that you'd ever write delete p+1 in a program is quite low, but that's beside the point...

Steve Jessop
@Steve Jessop: So, this has nothing to do with `p+1` not being allocated using `new()`?
Lazer
In the context of Stroustrup using it as an example for that FAQ question, no. In practice, if `p+1` results in an address that was allocated with `new()`, because `p` was obtained by subtracting 1 from that address, then in standard C++, `p` is not a valid pointer, and it is actually undefined behavior even to add 1 to it. Not something you'd expect to find yourself relying on. So the example was not a realistic one - Michael Mrozek's `p-1` is better. I think Stroustrup just picked `p+1` as an example of an lvalue, not as an example of something you'd actually delete.
Steve Jessop
"Example of an rvalue", I mean. Oops.
Steve Jessop
A: 

The section is talking about why delete() doesn't set the value of pointer variable to zero.

I'm not sure I can explain it better than the article. p != p+1.

Brian Roach