很多类似问题的回答都指出,标准是这样的。但是,我无法理解标准制定者做出这一决定背后的原因。
根据我的理解, anunsigned char不会以 2 的补码形式存储值。所以,我没有看到让我们说XOR ing twounsigned chars会产生意外行为的情况。因此,将它们提升到int似乎只是浪费空间(在大多数情况下)和 CPU 周期。
此外,为什么int?如果一个变量被声明为unsigned,显然无符号对程序员很重要,因此在我看来,升级到 anunsigned int仍然比 an 更有意义int。
[编辑 #1] 如评论中所述,unsigned int如果int无法充分容纳unsigned char.
[编辑#2] 为了澄清这个问题,如果它是关于在intthan上运行的性能优势char,那么为什么它在标准中?这可以作为向编译器设计者提供更好优化的建议。现在,如果有人要设计一个不这样做的编译器,这将使他们的编译器不完全遵守 C/C++ 标准,即使假设该编译器确实支持该语言的所有其他必需功能。简而言之,我无法弄清楚为什么我不能直接操作的原因unsigned chars,因此将它们提升到 的要求ints似乎没有必要。你能举个例子证明这是错误的吗?
您可以在线找到此文档:国际标准的基本原理 - 编程语言 - C (Revision 5.10, 2003)。
第 6.3 章(第 44 - 45 页)是关于转换的
在 K&R 的发布和 C89 的开发之间,整数提升规则的演变在实现之间出现了严重的分歧。实现分为两大阵营,其特征可能是未签名保留和值保留。
这些方法之间的区别集中在整数提升的处理
unsigned char和unsigned short扩大时,但该决定也对常量的类型产生影响(参见第 6.4.4.1 节)。该无符号保留方法要求促进两个较小的无符号的类型
unsigned int。这是一个简单的规则,并产生一个独立于执行环境的类型。该值保存方法要求促进这些类型
signed int,如果该类型可以正确表示原始类型的所有值,否则为促进这些类型unsigned int。因此,如果执行环境表示
short小于int,则unsigned short变为int; 否则就变成unsigned int. 在绝大多数情况下,这两种方案都给出了相同的答案,并且在更多情况下,在使用二进制补码算法和有符号溢出时的安静环绕的实现中,两者都给出了相同的有效结果 - 即在大多数当前实现中。在这样的实现中,只有当这两个条件都为真时才会出现两者之间的差异:
涉及
unsigned charor的表达式unsigned short会产生一个int-wide 结果,其中设置了符号位,即对此类类型进行一元运算,或另一个操作数为int“更窄”类型的二元运算。前面表达式的结果用于其符号性很重要的上下文中:
•
sizeof(int) < sizeof(long)并且在必须将其扩展为长类型的上下文中,或• 在此移位定义为算术的实现中,它是右移位运算符的左操作数,或
• 它是/、%、<、<=、> 或>= 的操作数。
在这种情况下,就会产生真正的歧义解释。结果必须被称为有问题的签名,因为可以为签名或未签名的解释做出案例。每当
unsigned intasigned int与运算符交叉时,都会出现完全相同的歧义,并且signed int具有负值。在解决这种对抗的模糊性方面,这两种方案都没有更好或更坏的效果。突然,负数signed int变得非常大unsigned int,这可能令人惊讶,也可能正是知识渊博的程序员所期望的。当然,所有这些歧义都可以通过明智地使用强制转换来避免。探索这个问题的重要结果之一是理解高质量的编译器可能会很好地寻找这些有问题的代码并提供(可选的)诊断,而认真的教师可能会很好地警告程序员隐式类型转换的问题.
无符号保留规则大大增加的情况下的数量
unsigned int面对signed int以产生可疑地签署结果,而值保持规则最小化这样的对抗。因此,对于新手或粗心的程序员来说,值保留规则被认为是更安全的。经过多次讨论,C89 委员会决定支持值保留规则,尽管事实上 UNIX C 编译器已经朝着无符号保留的方向发展。C89 中的安静变化
依赖于无符号保留算术转换的程序将表现不同,可能没有抱怨。这被认为是 C89 委员会对当前广泛使用的实践所做的最严重的语义更改。
作为参考,你可以找到有关此更新,C11这些转换详情答案由伦丁。
| 归档时间: |
|
| 查看次数: |
288 次 |
| 最近记录: |