Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Equality operand behavior for unsigned and signed types [duplicate]

Tags:

c++

c

Possible Duplicate:
Signed/unsigned comparisons

So I have the below code, which sets an unsigned int to a negative number, and then does a comparison of the unsigned int with the same negative number. The output I get is "Not Equal". I understand that when setting the unsigned int to -1, the value of the unsigned int is set to 255 in this case.

#include <stdint.h>
#include <iostream>

int main(int argc, char **argv)
{
  uint8_t test = 0;
  int8_t set = -1;

  test = set;

  if (test == set) {
    std::cout << "Equal";
  } else {
    std::cout << "Not Equal";
  }
}

However, what causes the equality operand to return false? This seems to be in direct contrast with the answer to the similar question Signed/unsigned comparisons which states

Many binary operators that expect operands of arithmetic or enumeration type cause conversions and yield result types in a similar way. The purpose is to yield a common type, which is also the type of the result. This pattern is called the usual arithmetic conversions, which are defined as follows:

If either operand is of type long double, the other shall be converted to long double.

Otherwise, if either operand is double, the other shall be converted to double.

Otherwise, if either operand is float, the other shall be converted to float.

Otherwise, the integral promotions (4.5) shall be performed on both operands.54)

Then, if either operand is unsigned long the other shall be converted to unsigned long.

Otherwise, if one operand is a long int and the other unsigned int, then if a long int can represent all the values of an unsigned int, the unsigned int shall be converted to a long int; otherwise both operands shall be converted to unsigned long int.

Otherwise, if either operand is long, the other shall be converted to long.

Otherwise, if either operand is unsigned, the other shall be converted to unsigned.

Thus according to this answer, since both operand is unsigned, the other shall be converted to unsigned, and the equality should pass. But it clearly is not passing, and as answered already in this question, they are both being promoted as signed ints.

like image 264
umps Avatar asked Jan 15 '23 02:01

umps


1 Answers

It is, indeed, standard behavior. Types that are smaller than int are promoted to int when used with == and most other operators. So test gets promoted to int, with the value 255. And set gets promoted to int, but it's a negative number, so its value, both before and after promotion, is -1. Since 255 is not equal to -1, the comparison gives false.

The moral is: be careful if you mix signed and unsigned types in comparisons.

like image 105
Pete Becker Avatar answered Jan 29 '23 12:01

Pete Becker