【问题标题】:Get last two characters from char array elements从 char 数组元素中获取最后两个字符
【发布时间】:2021-10-10 11:17:45
【问题描述】:

尝试打印数组元素,如下所示

typedef struct Info
{
char MacAdd[2];                      
} Info;

char MAC[100];

sprintf(MAC, "%x:%x%c", Info->MacAdd[0], Info->MacAdd[1],'\0');

printf("MAC %s",MAC);

得到的输出是 --> ffffff98:ffffffa4

如何获得类似 ---> 98:a4 的输出

【问题讨论】:

  • MacAdd重新声明为unsigned
  • Info->MacAdd 是如何定义的?从输出来看,看起来这些是带负值的有符号整数?顺便说一句,您不需要空终止,sprintf 无论如何都会这样做(除非您想要重复的空字符)。你觉得还是不错的...
  • 您的sprintf 呼叫中不需要%c'\0'sprintf 会为您解决这个问题。
  • 要始终打印两个字符,即使是个位数的值,请尝试 %.2x%02x
  • 更新了问题,请检查一下

标签: arrays c char


【解决方案1】:

Info 结构中的MacAdd 数组被声明为char 的数组。但char 通常是signed 类型。

当您调用printf 时,会发生某些“默认参数转换”。除其他外,类型char 被提升为int。而且由于 0x98 作为有符号字符实际上是负数(它是 -104),当这种情况发生时它会自动符号扩展——这就是额外的ff 的来源。 ffffff98 的值是 -104 的 32 位有符号版本,因此该值已被保留。

至少有三种方法可以解决这个问题,我认为按照从最吸引人到最不吸引人的顺序:

  1. MacAdd 数组重新声明为unsigned char 数组。
  2. 将 printf 格式更改为"%hhx:%hhx"hh 告诉 printf 您的值最初是 char,这会要求 printf 撤消促销,实际上是去掉不需要的 ff
  3. 将呼叫更改为sprintf(MAC, "%x:%x", Info->MacAdd[0] & 0xff, Info->MacAdd[1] & 0xff);

正如@Aconcagua 在评论中指出的那样,一旦您摆脱了ff,您可能还需要稍微调整一下您的 printf 格式,以处理个位数的地址。


脚注:上面的解决方案 3 相当糟糕,我不会认真推荐它。这是我们在 Ritchie 最初的 C 编译器时代使用的东西,当时还没有发明 unsigned char%hhx

【讨论】:

  • 通常是有符号类型 不。在许多系统上它是无符号的。可以签名是的。
  • 另外:大多数编译器都提供了一个选项来显式控制签名...
  • @12431234123412341234123 我不会对此进行冗长的争论,而且我说这个时只是部分认真,但是:对于我使用过的 100% 的编译器,还有更多重要的是,对于 GNK 使用的 100% 的编译器,char 类型实际上是有符号的。所以我支持“通常”这个词。 :-)
  • @SteveSummit 这通常取决于系统而不是编译器。 AMD64 上的 GCC 使用有符号,ARM 上的 GCC 使用无符号。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-10-13
  • 2020-07-03
  • 2020-12-03
  • 2020-04-30
  • 2021-05-15
  • 1970-01-01
  • 2020-12-08
相关资源
最近更新 更多