C

时间:2018-02-27 04:12:46

标签: c integer-promotion

void foo(void) {
    unsigned int a = 6;
    int b = -20;

    if (a+b > a) {
        printf("> a");
    } else {
        printf("< a");
    }
}

我试图了解上面的整数提升示例发生了什么。我知道,对于a = 6b = -20,由于> a被提升为b,因此输出应为unsigned int。但是,如果我指定< a,则输出会转到b = -5。在这种情况下输出也不应该相同,因为值b = -5也被提升为unsigned int

1 个答案:

答案 0 :(得分:9)

这样做的原因与签名值转换为无符号的方法有关。

关于有符号和无符号整数转换的C standard第6.3.1.3节规定了这种情况的发生方式:

  

2 否则,如果新类型是无符号的,则通过重复添加或减去一个超过最大值的值来转换该值   可以用新类型表示,直到值在范围内   新类型。 60)

     

...

     

60)规则描述了数学值的算术,而不是给定类型表达式的值。

b等于-20的示例中,当转换为无符号UINT_MAX + 1时,会将其添加到值中,因此转换后的值为UINT_MAX - 19。然后,当您添加a(6)的值时,您将获得UINT_MAX - 13。该值大于a,因此会打印"> a"

如果将b设置为-5,则转换后的值为UINT_MAX - 4。在此处添加6可为您提供UINT_MAX + 2。由于unsigned int值的数学模拟以UINT_MAX + 1为模,因此实际结果为1.这小于6,因此打印"< a"

此外,这里发生的不是整数提升,而是整数转换。如果表达式中的任何整数类型的排名小于int,则首先进行促销。情况并非如此。