Jurica Smircic
Jurica Smircic

Reputation: 6445

++ -- Operator precedence puzzle

For the long time I thought I get it, and I was going to create some puzzles to learn some of my „students“ on the topic of operator precedence in c#. But it came out that I still don't get it right. 

Puzzles: What’s the output here?

int a = 0;            
int x = --a + a++;
Console.WriteLine(x);
Console.WriteLine(a);

Output:

-2 0

All clear here, I expected this

Next, the problem one:

int b = 0;
int y = b-- + b++;
Console.WriteLine(y);
Console.WriteLine(b);

Output:

-1 0

Well, here I also expected y to be -2… Now I’m trying to apply operator precedence rules and order of evaluation, and not sure I explained it to myself. Read this post again few times today, but still don’t quite get it why is the result here -1? Can someone help with how is the second result evaluated. why and how is it different than the first one?

Upvotes: 7

Views: 432

Answers (5)

Tergiver
Tergiver

Reputation: 14517

This question has been answered, but I wanted to state the answer another way.

int b = 0;
int y = b-- + b++;

The expression b-- evaluates to 0 (the original value of b) and has the side effect (applied after evaluation) of decrementing b to -1.

The expression b++ evaluates to -1 (because of the previous side effect) and has the side effect (applied after evaluation) of incrementing b to 0.

This leaves the expression 0 + -1 which is -1.

Upvotes: 0

Eric Lippert
Eric Lippert

Reputation: 660148

Do what the compiler does: break it down slowly and surely into equivalent programs.

int b = 0;
int y = b-- + b++;

is equivalent to

int b, y;
b = 0;
y = b-- + b++;

is equivalent to

int b, y;
b = 0;
int leftAddend = b--;
int rightAddend = b++;
y = leftAddend + rightAddend;

is equivalent to

int b, y;
b = 0;
int originalb1 = b;
int newb1 = originalb1 - 1;
b = newb1;
int leftAddend = originalb1;
int originalb2 = b;
int newb2 = originalb2 + 1;
b = newb2;
int rightAddend = newb2;
y = leftAddend + rightAddend;

And now annotate each with its value:

int b, y;
b = 0;                       // b is now 0
int originalb1 = b;          // originalb1 is now 0
int newb1 = originalb1 - 1;  // newb1 is now -1
b = newb1;                   // b is now -1
int leftAddend = originalb1; // leftAddend is now 0
int originalb2 = b;          // originalb2 is now -1 
int newb2 = originalb2 + 1;  // newb2 is now 0
b = newb2;                   // b is now 0
int rightAddend = originalb2;// rightAddend is now -1
y = leftAddend + rightAddend;// y is now -1

This is precisely how the compiler deals with this situation; the compiler is just a bit more clever about optimizing away the temporaries. Analyzing expressions gets easy if you just break it down into simpler steps.

Upvotes: 10

porges
porges

Reputation: 30580

Postfix --/++ returns the original value of the variable. So:

With your example b-- + b++:

  • b-- means decrement b, return the original value. So b = b - 1, b is now -1, and the value of the expression is 0.
  • b++ means increment b, return the original value. So b = b + 1, b is now 0, and the value of the expression is -1.
  • Then, 0 + -1 == -1. This is y. b is still 0.

Upvotes: 0

Madbreaks
Madbreaks

Reputation: 19539

int b = 0;
int y = b-- + b++;

Break it down by step:

y = b--

Here, y is set to b (0), then b is decremented to -1.

+ b++

Here, y (0) is added to b (decremented to -1 in prev step) equaling -1, then b is incremented to zero. Output:

-1 0

Upvotes: 2

Robert Harvey
Robert Harvey

Reputation: 180808

b-- is post-decrement. So:

b-- returns zero and subtracts 1 from b, leaving -1 in b.

b++ returns the -1 from the last step and adds 1, leaving 0 in b.

Final result of the addition: -1.

Upvotes: 15

Related Questions