静态存储持续时间初始化

2024-02-24

在 C++ 中,静态存储持续时间对象以未指定的顺序初始化(同一编译单元中的除外)。

代码如下:

#include <iostream>

struct Foo {
    Foo() {
        std::cout << "Hello, world.\n";
    }
} foo_instance;

int main(int argc, const char *argv[]) {
    return 0;
}

标准中规定的位置我已经可以使用std::cout在初始化期间foo_instance?

我知道我可以通过添加一些技巧来确保事情顺利进行<iostream>,例如让它包含类似的东西

int __ensure_stdout_initialization_call();
namespace {
    int __ensure_stdout_initialization
      = __ensure_stdout_initialization_call();
}

然而,问题在于如何保证标准库所需的所有初始化都完成此操作。


太长;博士;你不应该使用std::cout在初始化期间foo_instance.

无论标准中标准流的初始化,唯一的要求是

27.4.1 概述 [iostream.objects.overview]

3 在第一次创建类对象之前或期间的某个时间构造对象并建立关联ios_base::Init被构造,并且无论如何在 main 主体开始执行之前。 291 程序执行期间对象不会被破坏。第292章 包括的结果<iostream>在翻译单元中应如同<iostream>定义了一个实例ios_base::Init具有静态存储时间。

所以如果你包括<iostream>在声明静态变量之前,您将被保存,因为根据标准

3.6.3 非局部变量的动态初始化[basic.start.dynamic]

2 具有静态存储持续时间的非局部变量 V 和 W 的动态初始化顺序如下: (2.1) 如果 V 和 W 已排序初始化,并且在单个翻译单元内 V 定义在 W 之前,则 V 的初始化将排序在 W 的初始化之前。

so ios_base::Init将在你的变量和标准流准备好之前初始化,但如果你声明你的变量,你似乎仍然可以射中自己的腿before包括<iostream>:

struct Foo
{
    Foo();
} foo_instance; // uses ::std::cout

#include <iostream> // declares ios_base::Init variable that will init ::std::cout

Foo::Foo()
{
    std::cout << "Hello, world.\n";
}

int main(int argc, const char *argv[]) {
    return 0;
}

垂死的例子 http://ideone.com/7dJG1J

所以我可以得出结论,在非局部变量的动态初始化期间不能使用 std::cout 。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

静态存储持续时间初始化 的相关文章

随机推荐