25

In The this pointer [class.this], the C++ standard states:

The type of this in a member function of a class X is X*.

i.e. this is not const. But why is it then that

struct M {
    M() { this = new M; }
};

gives

error: invalid lvalue in assignment  <-- gcc
'=' : left operand must be l-value   <-- VC++
'=' : left operand must be l-value   <-- clang++
'=' : left operand must be l-value   <-- ICC
(source: some online compiler frontends)

In other words, this is not const, but it really is!

Sebastian Mach
  • 36,158
  • 4
  • 87
  • 126

1 Answers1

45

Because in the same paragraph, it is also mentioned that this is a prvalue ("pure rvalue").

Examples mentioned in the standard for pure rvalue are the result of calling a function which does not return a reference, or literals like 1, true or 3.5f. The this-pointer is not a variable, it's more like a literal that expands to the address of the object for which the function is called ([class.this]). And like e.g. literal true has type bool and not bool const, this is of type X* and not X*const.

Sebastian Mach
  • 36,158
  • 4
  • 87
  • 126
  • 3
    @busy_wait In C++, values have a *type* and a *value category.* The type of `this` is `X*`, its value category is prvalue. How is this non-inituitive? `this` has to be a prvalue (`&this` makes no sense) - why make its type `X * const` when it's unmodifiable already? – Angew is no longer proud of SO Jun 17 '13 at 12:12
  • 3
    @Angew: One would have to add that there are languages where `this` (or its equivalent) isn't unmodifiable. E.g. python: `class X: def __init__(self): self = X() s = X()` – Sebastian Mach Jun 17 '13 at 12:15
  • So clear and concise +1. I understand c++ more now :) (mainly the explanation of pure rvalues). – Sellorio Jun 17 '13 at 12:21
  • Why does `&this` make no sense? What is the advantage of this method of passing `this` over passing it explicitly as a pointer, beyond cleaner code, of course? – idoby Jun 17 '13 at 12:35
  • @busy_wait `this` is a "pointer to the current instance." What would you expect the address of such a pointer to be? – Angew is no longer proud of SO Jun 17 '13 at 12:44
  • Somewhere on the current stack frame. I'm guessing this is also the actual mechanism of transmission of the data, right? – idoby Jun 17 '13 at 12:49
  • 5
    @busy_wait: No. It's formally unspecified, but e.g. MSVC++ uses the `ECX` register. You can´t take the address of a register. – MSalters Jun 17 '13 at 13:39
  • @MSalters Very well, that's the kind of answer I was looking for. – idoby Jun 17 '13 at 14:36
  • 1
    @busy_wait: As phresnel said, there are languages that allow you to modify the this pointer. Objective-C, for example. And it also make very good use of that, because this freedom (along with some others) make it possible for an abstract base class to silently provide instances of its subclasses, exchanging the object as it is initialized. Perfect for implementation hiding. Or for a constructor to return an already existing object, ensuring equivalence of identity and equality, etc. I had a case myself where I'd been glad to be able to do such tricks in C++, but alas, it's not going to be... – cmaster - reinstate monica Jun 17 '13 at 19:40