微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

为什么在 C++ 中将有符号字符分配给无符号字符时从 256 中减去?

如何解决为什么在 C++ 中将有符号字符分配给无符号字符时从 256 中减去?

在 Bjarne 的“The C++ Programming Language”一书中,给出了以下关于字符的代码

signed char sc = -140;
unsigned char uc = sc;
cout << uc // prints 't'

1Q) 个字符在我的硬件中是 1 字节(8 位)。 -140 的二进制表示是什么?是否可以使用 8 位表示 -140。我认为在考虑签名字符时,范围保证至少为 [-127...127]。怎么可能用 8 位表示 -140?

2Q) 假设这是可能的。当 140 分配给 uc 时,为什么我们要从 sc 中减去 uc?这背后的逻辑是什么?

编辑:我写了 cout << sizeof (signed char) 并且它产生了 1(1 个字节)。我把这个精确到 signed char 的字节大小。

EDIT 2: cout << int {sc } 给出输出 116。我不明白这里发生了什么?

解决方法

将 -140 分配给 signed char 的结果是实现定义的,就像它的范围一样(即参见手册)。一个非常常见的选择是使用环绕式数学:如果它不适合,加或减 256(或相关的最大范围)直到适合。

由于 sc 的值为 116,而 uc 也可以保存该值,因此该转换是微不足道的。当我们将 -140 分配给 sc 时,不寻常的事情已经发生了。

,

首先:除非您正在编写需要位表示操作的非常低级的东西 - 避免编写像瘟疫一样的代码。它难以阅读、容易出错、令人困惑,并且经常表现出实现定义/未定义的行为。

回答你的问题:

代码假设您在一个平台上,其中 signed charunsigned char 类型有 8 位(尽管理论上它们可以有更多)。并且硬件具有 "two's complement" 行为:N 位整数类型的算术运算结果的位表示总是模 2^N。这也指定了如何将相同的位模式解释为有符号或无符号。现在,-140 模 2^8 是 116 (01110100),因此位模式 sc 将成立。解释为有符号字符(-128 到 127),这仍然是 116。

unsigned char 也可以表示 116,因此第二个赋值的结果也是 116。

116 是字符 tASCII code;和 std::coutunsigned char 值(低于 128)解释为 ASCII 代码。所以,这就是打印出来的内容。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。