【问题标题】:Difference of uninitialized values for g++ and g++14g++ 和 g++14 的未初始化值的差异
【发布时间】:2019-11-17 11:37:41
【问题描述】:

如果我像这样在 c++ 中编译并运行一个简单的程序:

int main(){
    int x;
    cout << x << endl;
}

我在 Linux 中编译时说 g++ myProgram.cc(或 g++ -std=c++14),显然我得到了运行良好的 ./a.out 可执行文件,并打印了自动初始化的值 0。

但是如果我使用 g++14 myProgram.cc 编译我的代码,我会收到一条错误消息,指出 x 未初始化。

g++14 是某种不同的版本吗?我很困惑为什么会这样,谢谢!

【问题讨论】:

  • 两者都不是。出于某种原因,只是一个编译器仅在 C++14 中发出诊断。无论是C++11,还是C++14,或者任何C++版本,上面的程序都是未定义的行为,并且被破坏了。
  • 哦,它坏了?我认为未初始化值的 C++ 标准对于数字是 0,对于字符和字符串是空的。以及结构和类的默认构造函数,这不是真的吗?无论如何我都应该避免这样做吗? @SamVarshavchik
  • 我们无法知道g++14 是什么。这取决于您的系统是如何设置的,它与 C++ 无关。您可以尝试运行which g++14 来确定使用该文件时执行的文件并查看它。我怀疑它只是简单地调用g++ -std=c++14,这意味着它默认编译为 C++ 14 版本的 C++。
  • 这仅适用于静态范围的值。不是自动存储。
  • @ming 这是错误的。本地自动变量在默认初始化后具有不确定的值(这是您在此处使用的)。您总是需要显式地使用一个值进行初始化。但是,这不适用于具有静态存储持续时间的变量(例如全局变量)。无论是否有警告/错误消息,您的程序都有未定义的行为。是的,您应该始终初始化变量,无论它们的范围如何。

标签: c++


【解决方案1】:

自动初始化的值 0 打印出来。

不,一千次,不:-)

自动变量隐式初始化(a)。特定的实现可能会将它们初始化为特定值,但这不是标准强制或保证的。

您的问题的解决方案显式初始化它(或者在您尝试使用它之前分配给它)。

换句话说,使用:

int x = 0;

(a) 具有构造函数的类或结构显然已初始化,但此处并非如此,因为您使用的是简单的 int 类型。

【讨论】:

    【解决方案2】:

    来自 C++ 参考的initialization 部分(适用于所有版本)。您可以推断出局部非静态原始类型变量在声明时不会自动初始化为众所周知的值/状态,您必须明确地进行。请注意,虽然没有被初始化,但它们确实包含一个值,但它不是确定性的,它可以是任何东西,因此您对 显式初始化 的(最重要的)重要性。因此,确保变量具有众所周知和定义的状态。您的代码实际上展示了所谓的未定义行为,因为它使用了一个具有未知和未定义值/状态的变量。

    这适用于所有版本的 C++。因此:

    • 您的编译器可能存在错误,对于初始化规则这样简单的事情不太可能发生。

    • 这可能是您的编译器的实现特定细节。

    • 该命令可能正在调用其他东西

    作为一种好的做法,这将使您免于将来出现许多错误,始终在使用之前尽快初始化您的变量

    【讨论】:

      【解决方案3】:

      g++ -std=c++14 g++14

      gcc 在某些地方很不稳定:

      From another post about GCC

      没有“官方的GCC定义”,只有官方的英文定义。

      这段话的意思是,GCC 在 C++14 发布之前已经实现了当时即将推出的 C++14 特性的实验原型,而未来的版本将不会费心尝试保持与这些实验的向后兼容性。

      两个版本之间的向后兼容性仅针对这些版本中包含的国际标准中的功能进行维护。

      这是因为,在标准发布之前,新 C++ 功能的规范可能会发生相当大的变化。保证支持它们的早期实验将与最终在标准中发布的最终真实功能向前兼容,这将是疯狂的。

      简而言之:使用实验性功能需要您自担风险,不要期望它们在 GCC 的下一个版本中以同样的方式工作。

      【讨论】:

        猜你喜欢
        • 2015-03-22
        • 1970-01-01
        • 1970-01-01
        • 2012-11-09
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-07-24
        相关资源
        最近更新 更多