I want the following idea: I have short a = -4; and I have an unsigned short b = (unsigned short)a;
When I printf("%hu", b), why doesn't it print 4? How can I convert a negative integer to a positive integer using casting?
I want the following idea: I have short a = -4; and I have an unsigned short b = (unsigned short)a;
When I printf("%hu", b), why doesn't it print 4? How can I convert a negative integer to a positive integer using casting?
short and unsigned short are normally 16 bit integers. So limits are -32768 to 32767 for the signed version (short) and 0 to 65535 for unsigned short. Casting from signed to unsigned just wraps values, so -4 will be casted to 65532.
This is the way casting to unsigned works in C language.
If you accept to use additions/substractions, you can do:
65536l - (unsigned short) a
The operation will use the long type (because of the l suffix) which is required to be at least a 32 bits integer type. That should successfully convert any negative short integer to its absolute value.
It sounds like you want the absolute value of the number, not a cast. In C we have the abs / labs / llabs functions for that, found in <stdlib.h>.
If you know ahead of time that the value is negative, you can also just negate it: -a.
If you were instead just looking to get the absolute value, you should have used the abs() function from <stdlib.h>.
Otherwise, when you make such a cast, you trigger the following conversion rule from C17 6.3.1.3:
Otherwise, if the new type is unsigned, the value is converted by repeatedly adding or subtracting one more than the maximum value that can be represented in the new type until the value is in the range of the new type. 60)
Where foot note 60) is important:
- The rules describe arithmetic on the mathematical value, not the value of a given type of expression.
Mathematical value meaning we shouldn't consider wrap-around etc when doing the calculation. And the signedness format (2's complement etc) doesn't matter either. Applying this rule, then:
-4 and convert from signed short to unsigned short.-4 + USHRT_MAX + 1, where UINT_MAX is likely 2^16 = 65535.-4 + 65535 + 1 = 65532. This is in range of the new type unsigned short.This conversion is well-defined and portable - you will get the same result on all systems where short is 16 bits.