tags:

views:

221

answers:

7

How are the below valid and invalid as shown and what do they mean. When would such a situation arise to write this piece of code.

++x = 5;     // legal
--x = 5;     // legal
x++ = 5;     // illegal
x-- = 5;     // illegal
+11  A: 

The postfix (x++/x--) operators do not return an lvalue (a value you can assign into).

They return a temporary value which is a copy of the value of the variable before the change

The value is an rvalue, so you could write:

y = x++ and get the old value of x

Uri
You should add that code such as that should never be used.
Bruno Brant
@Bruno: Why not? That's the entire point to the post-increment operator.
Dennis Zickefoose
+8  A: 

Those all modify the value of x more than once between sequence points, and are therefore undefined behavior, which you should carefully avoid. I don't see where the distinction between "legal" and "illegal" comes in - since the behavior is legal, any behavior (including sending assorted email to the Secretary of State) is perfectly in accordance with the Standard.

David Thornley
+5  A: 

Assuming that the question is about built-in ++ and -- operators, none of these statements are strictly legal.

The first two are well-formed, i.e. they merely compilable because the result of prefix increment is lvalue. The last two are ill-formed, since the result of postfix increment is not a rvalue, which is why you can't assign to it.

However, even the first two are not legal in a sense that they produce undefined behavior. It is illegal to modify the same object more than once without an intervening sequence point. (Note also, that compilers are allowed to refuse to compile well-formed code that produces undefined behavior, meaning that even the first pair might prove to be non-compilable).

AndreyT
+8  A: 

Given that both operator=() and operator++() can be overloaded, it is impossible to say what the code does without knowing more about the type of thing the operators are being applied to.

anon
Curious to why this was downvoted - the man has a valid point. I expect that the OP is dealing in ints, but there's no type mentioned.
DeadMG
I believe it is even possible that this not result in undefined behavior if x is a non-scalar type.
Dennis Zickefoose
@DeadMG: People downvote things when they didn't think of them or think they are too "fancy" or "pedantic."
John Dibling
I didn't downvote, but maybe because this is more of a comment than an answer.
GMan
+1  A: 

Frankly, you should never write that. Postincrement and pre-increment (and decrements) should only ever be used on their own. They're just recipes for confusion.

DeadMG
If you only use them on their own, then post increment is a worthless operator.
Dennis Zickefoose
I think that when DeadMG said "on their own" he meant don't do double assignment. He didn't mean to exclude things like `if( x++ ) {/*...*/}` etc. Right, DeadMG?
John Dibling
I absolutely did mean to exclude those. Postincrement and pre-increment are syntactic sugar, not good when actually used in an expression. If you desperately need this, do it manually, let the compiler turn it into the other form. But I don't see in what possible condition you could need it anyway.
DeadMG
+1  A: 

The only place I can think of where such a situation would occur is with an operator overload of operator++ and operator=. Even then, the definition isn't clear. What you code is saying basically is add one to x, then assign 5 to it. A question would arise such as why would you need to increment x before assigning 5 to it? The only possible explanation is if you have some sort of class where the ++ operator somehow increment an internal counter, then the assignment. No idea why such a thing is needed though.

Daniel
+1  A: 

++x and --x both give you back x (after it's been incremented/decremented). At that point you can do what you want with it, including assign it a new value.

x++ and x-- both give you back what x was (just before it was incremented/decremented). Altering this value makes no more sense than changing any ordinary function's return value:

obj->getValue() += 3; // pointless
Dan Tao