为无符号类型分配符号文字时,为什么GCC不会产生警告?

时间:2010-05-05 08:19:06

标签: c gcc unsigned gcc-warning

本网站上的几个问题揭示了混合有符号和无符号类型时的缺陷,大多数编译器似乎都很好地生成了这种类型的警告。但是,GCC在将有符号常量赋值给无符号类型时似乎并不在意!请考虑以下程序:

/* foo.c */
#include <stdio.h>
int main(void)
{
    unsigned int x=20, y=-30;
    if (x > y) {
        printf("%d > %d\n", x, y);
    } else {
        printf("%d <= %d\n", x, y);
    }
    return 0;
}

使用GCC 4.2.1进行编译,如下所示在控制台上没有输出:

gcc -Werror -Wall -Wextra -pedantic foo.c -o foo

生成的可执行文件生成以下输出:

$ ./foo
20 <= -30

在将带符号值-30分配给无符号整数变量y时,是否有某些原因导致GCC不生成任何警告或错误消息?

3 个答案:

答案 0 :(得分:21)

使用-Wconversion

~/src> gcc -Wconversion -Werror -Wall -Wextra -pedantic -o signwarn signwarn.c
cc1: warnings being treated as errors
signwarn.c: In function 'main':
signwarn.c:5: error: negative integer implicitly converted to unsigned type

我想这里的事情是gcc实际上非常擅长生成警告,但默认情况下不会这样做(有时是意外的)。浏览可用的警告并选择一组产生您认为有用的选项是个好主意。或者只是所有这些,并抛光代码,直到它闪耀! :)

答案 1 :(得分:7)

将负值转换为无符号类型的功能是C语言的功能。因此,默认情况下不会发出警告。如果你愿意的话,你必须明确地要求它。

关于你的程序输出的内容......使用%d的{​​{1}}格式说明符和一个超出类型printf范围的无符号值会导致未定义的行为,这就是你真的在实验中观察到了。

答案 2 :(得分:2)

使用(无符号)-1是一种常用的方法来设置所有位,有时甚至引用C作为此(错误)功能的原因,即使是那些应该更了解的人 。它既不明显也不可移植 - 你想用来设置所有位的表达式是〜0。