Relational operators precision

107 views Asked by At

i have a question about relational operators are they always give correct results ? because if we run this line of code it will result 1 instead of 0

cout<<(ULLONG_MAX==-1);

and if we keep subtracting 1 of both sides it will keep resulting 1

so this could give wrong results in our programs

what is the solution to it?

2

There are 2 answers

1
Artyer On

Since you are looking for solutions:

Enabling warnings (-Wall or more specifically -Wsign-compare on clang or gcc) should give you a warning if you accidentally do this:

warning: comparison of integers of different signs: 'unsigned long long' and 'int' [-Wsign-compare]

And the fix is to make sure everything has the same type.

If you really meant to compare two objects of different types, you can use std::cmp_equal (or the example implementation if you can't use C++20):

std::cout << std::cmp_equal(ULLONG_MAX, -1);  // Outputs 0

which directly compares the values of the integers, regardless of the type.

1
Ted Lyngmo On

In this comparison

ULLONG_MAX == -1

You have one unsigned long long and one int. Before the values are being compared, the operands undergo integral promotion in which the int is promoted to unsigned long long, which is like doing static_cast<unsigned long long>(-1) so that the two operands have a common type.

Now, an unsigned long long can't hold the value -1 and it will then "wrap around" to become the largest possible unsigned long long - which is exactly the value ULLONG_MAX holds.

The comparison is therefore true and printing true will show 1 (unless std::boolalpha is in effect).