int a = ((int-1) * x; I suppose you meant int a = ((int)-1) * x;
assert(a == -5); // Assert fails!!!!!
I suppose you meant assert(b == -5); // Assert fails!!!!!
From TCPL K&R 2nd ed, if either operand of an arithmetic operation is unsigned int, the other is also converted to unsigned int and the result is also an unsigned int. (I'm only assuming the case where both are same width, e.g. unsigned int against signed int).
consider
int b = ((int)-1) * x / 2; which is actually
int b =( ((int)-1) * x )/ 2; if you care for the left associativity of the multiplication operator.
((int)-1) yields a integer -1 (note that this cast is useless). Since it is being multiplied by a unsigned int, -1 is promoted to a unsigned int. Any negative int when promoted to int will yield
smallest non-negative value that is congruent to that integer, modulo one more than the largest value that can be represented in the unsigned type. So it is a very large number(4294967286 on my machine)which when multiplied by 10 yields larger number which is again demoted to fit into a unsigned int. Now you divide that number by two and you get the result.(which is still a larger number)(2147483643 on my machine.
The funny part is: all this doesn't happens in the line previous to this. That is perhaps because of your compiler's smartness, it doesn't promote -1 to int but demotes x to a int. This is done as, there is no more operation to perform.
Anyways., the correct procedure would be
((int)-1) * (x / 2); which would yield the desired result.
Note that int(-1) is same as -1.
If I were you I would have chosen a statement like this:
int b = ( int(x)*(-1) ) /2;
The code tags are :
[code=cplusplus]
//code goes here
[/code]