tags:

views:

100

answers:

3
+2  A: 

The C language doesn't provide any way of specifying a literal with type char or unsigned char. Use the cast.

By the way, the result of your calculation is outside the range of unsigned char, so the warning is quite correct - conversion will alter its value. C doesn't provide arithmetic in any type smaller than an int. In this case I suppose that what you want is modulo-256 arithmetic, and I think that gcc will recognise that, and will not emit the warning with the casts in place. But as far as the C language is concerned, that calculation is done in the larger type and then converted down to unsigned char for storage in ascii.

Steve Jessop
My example overflows because I used "foo" rather than a real life example. Oops!
bobby
I actually did a bit of head-scratching about that, and realised that with ASCII it still works - the difference between `f` and `F` is 32, so once multiplied by 16 the difference vanishes mod 256, and you'll get the right answer, `0xF0`. I did wonder what you were planning to do about the `o`, though ;-)
Steve Jessop
A: 

You can specify character literals, of type charint (char in C++), with specific numbers using octal or hexadecimal notation. For example, \012 is octal 12, or decimal 10. Alternatively, you could write '\x0a' to mean the same thing.

However, even if you did this (and the calculation didn't overflow), it might not get rid of the warning, as the C language specifies that all operands are promoted to at least int (or unsigned int, depending on the operand types) before the calculation is done.

Doug
In `C`, "character literals" are of type `int`. `'\012'` is an int; `'\x0a'` is an int; ...
pmg
@pmg: Thanks, I should've checked...
Doug
+3  A: 

In C, you cannot do calculations in anything shorter than int

char a = '8' - '0'; /* '8' is int */
char a = (char)'8' - '0'; /* (char)'8' is converted to `int` before the subtraction */
char a = (char)'8' - (char)'0'; /* both (char)'8' and (char)'0' are converted */
pmg