想象一下:
int X;
X = X;
这将是未定义的行为
1 The behavior is undefined in the following circumstances:
[...]
The value of an object with automatic storage duration is used while it is indeterminate (6.2.4, 6.7.8, 6.8).
但是这个呢?
int X;
X;
在引用引用时调用 X;
是否会允许编译器导致未定义的行为?还是这不算 X 被“使用”了?
最佳答案
在 C 1999 中,使用未初始化的对象并不是直接的错误。 (您从附件 J 中引用的内容不是标准的规范部分;它们只是提供信息。)具有自动存储持续时间的未初始化对象具有不确定的值。对于某些对象,该值可能是陷阱表示,因此使用它可能会导致未定义的行为。
但是,对于某些对象,可以确定未初始化的对象不能有陷阱值。例如,unsigned char
不能有陷阱值,stdint.h
中定义的精确宽度有符号整数类型不能有陷阱值(因为它们是补码没有填充位)。对于其他类型,可能是您的 C 实现定义的属性导致它们没有陷阱值。使用未初始化的 int X
在所有 C 1999 实现中都没有定义的行为(但在某些实现中有),但使用未初始化的 unsigned char X
有。
在 C 2011 中,在 6.3.2 2 中添加了此文本:“如果左值指定一个自动存储持续时间的对象,该对象可以用register 存储类声明(从未有其地址采取),并且该对象未初始化(未使用初始化程序声明并且在使用之前未对其执行任何赋值),行为未定义。”因此,在 C 2011 中,X = X;
和 X;
都有未定义的行为。
历史/背景:
C 2011 更改支持 Hewlett-Packard 机器,该机器对某些寄存器有一个特殊标志,指示寄存器内容是否有效。如果寄存器在其内容无效时被使用,机器会产生异常。因此,如果编译器将unsigned char X
的X
赋值给这样一个寄存器,当它无效时使用该寄存器可能会导致机器异常,即使没有unsigned char
陷阱值。
关于调用 void 语句会导致未定义的行为吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19030602/