C ++ enum to unsigned int comparison
I found this in the code I am currently working on and thought that this was the cause of some of the problems that I ran into.
In the header somewhere:
enum SpecificIndexes{
//snip
INVALID_INDEX = -1
};
Then later - initialization:
nextIndex = INVALID_INDEX;
and use
if(nextIndex != INVALID_INDEX)
{
//do stuff
}
Debugging the code, the values ββin nextIndex don't quite make sense (they were very large) and I found that it was declared:
unsigned int nextIndex;
So the initial setting to INVALID_INDEX was insufficient for an unsigned integer and set it to a huge number. I assumed this was the cause of the problem, but if you look closely, the test
if(nextIndex != INVALID_INDEX)
Worked correctly, meaning it never executed the if body when nextIndex was "high + ve".
It is right? How does this happen? Is the enum value implicitly cast to an unsigned int of the same type as the variable, and therefore wrapped in the same way?
source to share
Yes to everything. This is valid code, it is also widely used on the C ++ library side, even more so in modern C ++ (it's weird the first time you see it, but its a very general pattern in reality).
The enums are then signed with ints, but they are implicitly translated into unsigned ints, now it depends on your compiler, may give a warning, but it is still very commonly used, however you have to explicitly make it clear to maintainers.
source to share
enums can be signed or unsigned integer types depending on whether they contain any negative values ββand what the compiler is. The example here contains a negative value and therefore must be represented by a signed integral type.
Equality comparison between signed and unsigned types is safe and usually does what the author intended - the signed value will first be converted to unsigned, and the result of doing this is defined by the C ++ standard and is intuitive (at least when you know the target type, the exception, perhaps, is if the integers are not two's complement, so it may not be intuitive, but usually not a problem).
Comparing orders is likely to lead to errors. For example:
SpecificIndexes value = INVALID_VALUE;
return (value >= 0);
returns false, but:
unsigned int value = INVALID_VALUE;
return (value >= 0);
returns true. Sometimes the author will not appreciate the difference, especially if the type "value" is not entirely obvious at the point of use. The compiler can be good at warning about the second example, though, since (value> = 0) is a tautology.
source to share
In fact, -1 is implicitly cast to its unsigned equivalent when it is assigned to nextValue. An unsigned designator is a value with the same bitwise representation (which is 111111111111 ..., which is the maximum unsigned value).
Further implicit casting occurs in the comparison instruction.
So this is working right now, but may cause problems in the future. Sign and unsigned values ββcannot be mixed.
source to share