【问题标题】:Uninitialized values being initialized?未初始化的值被初始化?
【发布时间】:2009-08-04 05:24:31
【问题描述】:

在 C 中,自动变量如果未初始化,则保存一个垃圾值。但是,请考虑以下程序:

int main(){
 signed char term;
 (char)term--;
 printf("%d\n",term);
}

它打印一个值'7'。如果我不做(char)term--,它会打印一个值'8'。所以,它绝对没有垃圾值。这不矛盾吗?

【问题讨论】:

    标签: c variables


    【解决方案1】:

    那是垃圾。你得到 8 作为垃圾,减去得到 7。

    这就是未定义的行为。仅仅因为你不断得到 8 并不意味着它是明确定义的。尝试在你的代码中做更复杂的事情。在char 的上方和下方添加变量。


    关于你的“测试”,你说:

    但是,考虑到垃圾应该是随机的,一致性很难被忽视。

    您需要检查您的假设。 “垃圾应该是随机的”是谁说的?垃圾应该根据什么随机?垃圾是随机的唯一方法是系统定期遍历内存并为其分配随机数。

    当我们说“随机”时,我们的意思是我们不知道它会是什么。这并不意味着它是不确定的。这些是计算机。如果你告诉他们一遍又一遍地做同样的事情,它会一遍又一遍地做同样的事情

    您的编译器和设置不断生成相同的代码,最终为您提供这些垃圾值。确定性,但您不能依赖这种行为:“随机”。

    另外,1-800 并不意味着你要像以前那样接受这个。 “8”不一定表示垃圾,因为在设置事物的方式中,您的编译器会用 8 填充它们。他的意思是 8 与任何其他数字一样垃圾。

    【讨论】:

      【解决方案2】:

      值 8 包含在被认为是“垃圾”或“未初始化”的数字集中。

      【讨论】:

        【解决方案3】:

        就值而言,垃圾是某些先前函数留在堆栈中的任何内容。更改 libc 或任何数量的东西,这个数量就会改变。

        【讨论】:

          【解决方案4】:

          您似乎混淆了“垃圾”和“非确定性”这两个术语。术语中的值被认为是垃圾,因为您无法控制其中的值。它可以从平台更改为平台或运行运行,即未定义的行为..

          另一方面,如果程序运行时环境中的所有东西都相等,那么每次运行的值可能都相同。然而,这并不排除它是垃圾。

          【讨论】:

          • 同意。如果您想了解,请尝试使用调试器单步执行代码,单步执行(可能是汇编模式),因为这将使您了解在 main() 之前运行的启动代码。
          【解决方案5】:

          它确实包含垃圾,它包含 8 位垃圾,并将二进制读取为 0-255 之间的数字(假装您使用无符号字符)。

          所以记忆可能是这样的:

          | 0 0 1 0 1 0 1 0 0 1 0 0 1 0 0 1 0 1 0 1 |

          它取了结尾 (1 0 0 1 0 1 0 1) 并将其读取为一个数字,即 149。它仅取决于指定长度的位置中的随机二进制文件(例如:unsigned char = 1个字节)

          如果它是一个无符号整数,它会占用 4 个字节的随机垃圾并使其成为一个数字。

          【讨论】:

            【解决方案6】:

            将其视为使用任意值(位模式)进行初始化。

            那个任意值取决于变量最后一次使用的堆栈位置,它绝对不是随机值。它可能总是也可能不总是相同的值。它可能取决于之前发生的任何其他事情。

            最好始终初始化自动变量以避免未定义的行为。

            【讨论】:

              【解决方案7】:

              感谢您的回答。我尝试了一点修改:

              int main(){
                         signed char term1;
                         signed char term2;
                         signed char term3;
                         printf("%d\n%d\n%d\n",term1,term2,term3);
              }
              

              我在 3 台不同的机器上运行该程序。结果在所有 3 台机器上都是相同的:term1 的值 = -124,term2 = 4 和 term3 = 8。如果我删除 term3,term1 = 4,term2 = 8。如果我删除 term2,term1 = 8。所以,基本上,最后一个被标记为有符号字符的值得到“8”的值。正如1800 INFORMATION所说,'8'是用来表示垃圾的值之一,可能就是这样。然而,考虑到垃圾应该是随机的,一致性是很难忽视的。

              【讨论】:

              • 计算机上没有什么是真正随机的。您可以使用 a 您可能会考虑在具有三种不同运行时和不同编译器的三种不同架构上尝试您的程序。例如 x86 windows 机器、x86 Linux 机器和 PowerPC Macintosh。我的猜测是你会得到不同的结果。您甚至可能使用不同的编译器得到不同的结果(例如,Visual Studio 2008 与 Visual C++ 6.0)。最根本的一点是它与 C 运行时环境不一致。
              猜你喜欢
              • 1970-01-01
              • 1970-01-01
              • 2014-12-29
              • 2020-02-08
              • 2021-11-11
              • 1970-01-01
              • 1970-01-01
              • 2021-04-11
              • 2017-10-30
              相关资源
              最近更新 更多