-1

I just stumbled across this: When postifix incrementing a bool twice, the integer value still is 1 instead of the expected 2. I'd like to know why this happens.

bool test = false; // results in integer 0
test++; // results in integer 1
test++; // results in integer 1

// but there still is at least one byte of memory used:
// results in integer 137
*(unsigned char*)(&test) = 137;
bricklore
  • 4,125
  • 1
  • 34
  • 62
  • Without looking at any machine code produced by this, I would assume that the compiler ignores all but the least significant *bit* when you've told it to work on a `bool`. It's also possible that `bool + 1` gets turned into `bool & 1` as an optimization or to prevent overflows, which would cause the behavior you're seeing. The compiler could be doing some even more clever; you should really include the assembly for this bit of code. – ssube Jun 24 '13 at 16:52
  • A `bool` can only be either `true` or `false`, setting it to 137 is undefined behavior – David Rodríguez - dribeas Jun 24 '13 at 17:10

3 Answers3

8

This is how the ++ operator is specified. See C++11 §5.2.6[expr.post.incr]/1 (emphasis mine):

The value of a postfix ++ expression is the value of its operand. [Note: the value obtained is a copy of the original value —end note] The operand shall be a modifiable lvalue. The type of the operand shall be an arithmetic type or a pointer to a complete object type.

The value of the operand object is modified by adding 1 to it, unless the object is of type bool, in which case it is set to true. [Note: this use is deprecated, see Annex D. —end note]

(The prefix ++ operator has similar language to allow it to be applied to a bool value.)

Modifying the bool object through a pointer or reference of a type other than bool yields undefined behavior.

Community
  • 1
  • 1
James McNellis
  • 348,265
  • 75
  • 913
  • 977
  • I'm guessing applying `--` to a `bool` would set it to `false`, then, regardless of its prior state? – JAB Jun 24 '13 at 16:53
  • @JAB: No. Neither the prefix nor the postfix `--` may be applied to an operand of type `bool`. – James McNellis Jun 24 '13 at 16:54
  • 1
    Aliasing through `unsigned char` is allowed, though. The UB doesn't come from just modifying it, it comes from writing a value not in the value representation of `bool`. This is fine: `bool d, s = true; std::memcpy(&d, &s, sizeof(bool)); /* loop char by char */` for example. – GManNickG Jun 24 '13 at 16:59
0

why is this possible?!

Undefined behaviour is just that - undefined. Anything at all could happen.

if enough memory for 137 is allocated, then why the hell test++; results in 1?

The language specification defines that behaviour.

Carl Norum
  • 219,201
  • 40
  • 422
  • 469
0

Because you've invoked undefined behavior by casting a pointer to a different type and performing read/write on it. UB = anything can happen, including nasal demons.

Edward Strange
  • 40,307
  • 7
  • 73
  • 125