简体   繁体   English

在 C 中将 unsigned char 和 signed char 类型转换为 int

[英]typecasting unsigned char and signed char to int in C

int main()
{
  char ch1 = 128;
  unsigned char ch2 = 128;
  printf("%d\n", (int)ch1);
  printf("%d\n", (int)ch2); 
}

The first printf statement outputs -128 and second 128. According to me both ch1 and ch2 will have same binary representation of the number stored: 10000000. So when I typecast both the values to integers how they end up being different value?第一个 printf 语句输出 -128 和第二个 128。根据我的说法,ch1 和 ch2 都将具有相同的二进制表示存储的数字:10000000。那么当我将这两个值都转换为整数时,它们最终如何成为不同的值?

First of all, a char can be signed or unsigned and that depends on the compiler implementation.首先,一个char可以是有signedunsigned的,这取决于编译器的实现。 But, as you got different results.但是,当你得到不同的结果时。 Then, your compiler treats char as signed .然后,您的编译器将char视为signed

A signed char can only hold values from -128 to 127. So, a value of 128 for signed char overflows to -128 .signed char只能保存从 -128 到 127 的值。因此,有符号字符的 128 值会溢出到-128

But an unsigned char can hold values from 0 to 255. So, a value of 128 remains the same.但是unsigned char可以保存从 0 到 255 的值。因此,128 的值保持不变。

An unsigned char can have a value of 0 to 255 . unsigned char的值可以是0255 A signed char can have a value of -128 to 127 .signed char的值可以是-128127 Setting a signed char to 128 in your compiler probably wrapped around to the lowest possible value, which is -128 .在编译器中将有signed char设置为128可能会环绕到可能的最低值,即-128

For starters these castings对于初学者来说,这些铸件

printf("%d\n", (int)ch1);
printf("%d\n", (int)ch2);

are redundant.是多余的。 You could just write你可以写

printf("%d\n", ch1);
printf("%d\n", ch2);

because due to the default argument promotions integer types with the rank that is less than the rank of the type int are promoted to the type int if an object of this type can represent the value stored in an object of an integer type with less rank. because due to the default argument promotions integer types with the rank that is less than the rank of the type int are promoted to the type int if an object of this type can represent the value stored in an object of an integer type with less rank.

The type char can behave either as the type signed char or unsigned char depending on compiler options.根据编译器选项, char类型可以表现为signed char类型或unsigned char类型。

From the C Standard (5.2.4.2.1 Sizes of integer types <limits.h>)来自 C 标准(5.2.4.2.1 尺寸 integer 类型 <limits.h>)

2 If the value of an object of type char is treated as a signed integer when used in an expression, the value of CHAR_MIN shall be the same as that of SCHAR_MIN and the value of CHAR_MAX shall be the same as that of SCHAR_MAX. 2 如果在表达式中使用 char 类型的 object 的值作为带符号的 integer 处理,则 CHAR_MIN 的值应与 SCHAR_MIN 的值相同,CHAR_MAX 的值应与 SCHAR_MAX 的值相同。 Otherwise, the value of CHAR_MIN shall be 0 and the value of CHAR_MAX shall be the same as that of UCHAR_MAX.否则,CHAR_MIN 的值应为 0,CHAR_MAX 的值应与 UCHAR_MAX 的值相同。 20) The value UCHAR_MAX shall equal 2CHAR_BIT − 1. 20) UCHAR_MAX 值应等于 2CHAR_BIT - 1。

So it seems by default the used compiler treats the type char as signed char.因此,默认情况下,使用的编译器似乎将 char 类型视为带符号的 char。

As a result in the first declaration作为第一个声明的结果

char ch1 = 128;  
unsigned char ch2 = 128;

the internal representation 0x80 of the value 128 was interpreted as a signed value because the sign bit is set.128的内部表示0x80被解释为有符号值,因为设置了符号位。 And this value is equal to -128.而这个值等于-128。

So you got that the first call of printf outputted the value -128所以你得到了 printf 的第一次调用输出值 -128

printf("%d\n", (int)ch1);

while the second call of printf where there is used an object of the type unsigned char而 printf 的第二次调用使用了无符号字符类型的 object

printf("%d\n", (int)ch2);

outputted the value 128.输出值 128。

Your fundamental error here is a misunderstanding of what a cast (or any conversion) does in C.您在这里的基本错误是误解了 C 中的演员表(或任何转换)的作用。 It does not reinterpret bits.它不会重新解释位。 It's purely an operation on values .这纯粹是对values的操作。

Assuming plain char is signed, ch1 has value -128 and ch2 has value 128. Both -128 and 128 are representable in int , and therefore the cast does not change their value.假设普通char已签名,则ch1的值为 -128, ch2的值为 128。 -128 和 128 都可以在int中表示,因此强制转换不会改变它们的值。 (Moreover, writing it is redundant since the default promotions automatically convert variadic arguments of types lower-rank than int up to int .) Conversions can only change the value of an expression when the original value is not representable in the destination type. (此外,编写它是多余的,因为默认促销会自动将类型低于int的可变参数 arguments 转换为int 。)只有当原始值在目标类型中不可表示时,转换才能更改表达式的值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM