C / C ++以十六进制格式打印字节,获得奇怪的十六进制值

时间:2018-02-02 10:03:05

标签: c++ c

我使用以下内容从十六进制数组中打印出数字:

char buff[1000];

// Populate array....

int i;
for(i = 0; i < 1000; ++i)
{
    printf("[%d] %02x\n", i,buff[i]);
}

但我有时打印出奇怪的值:

byte[280] 00     
byte[281] 00     
byte[282] 0a     
byte[283] fffffff4         // Why is this a different length?
byte[284] 4e      
byte[285] 66      
byte[286] 0a   

为什么打印'fffffff4'?

2 个答案:

答案 0 :(得分:10)

使用%02hhx作为格式字符串。

来自CppReference%02x接受unsigned int。当您将参数传递给printf() variadic function时,buff[i]会自动转换为int。然后格式说明符%02x使printf()将值解释为int,因此像(char)-1这样的潜在负值会被解释并打印为(int)-1,这是原因你所观察到的。

还可以推断,您的平台已签署char类型和32位int类型。

长度修饰符hh会告诉printf()解释以[{1}}类型提供的内容,因此char%hhx的正确格式说明符。

或者,您可以在打印前将数据转换为unsigned char。像

unsigned char

这也可以防止负值显示太长,因为printf("[%d] %02x\n", i, (unsigned char)buff[i]); 可以(几乎)始终包含int值。

请参阅以下示例:

unsigned char

上述程序的输出是:

#include <stdio.h>

int main(){
    signed char a = +1, b = -1;
    printf("%02x %02x %02hhx %02hhx\n", a, b, a, b);
    return 0;
}

答案 1 :(得分:5)

您的平台显然已签署char。在char未签名的平台上,输出将为f4

调用variadic function时,任何小于int的整数参数都会提升为int

charf4-12signed char)的符号位已设置,因此转换为int时变为fffffff4 (在你的情况下仍为-12但现在为signed int)。

%x02会导致printf将参数视为unsigned int,并使用至少 2个十六进制数字打印它。 输出不适合2位数,因此使用了许多。

因此输出fffffff4

要解决此问题,请声明数组unsigned char buff[1000];或转换参数:

    printf("[%d] %02x\n", i, (unsigned char)buff[i]);