1

考虑下面的程序:(见现场演示here.C++的命名空间范围的初始化变量

#include <iostream> 
inline double fun() 
{ 
    return 3.0; 
} 
extern double m; 
double d2=m; 
int main() 
{ 
    std::cout<<d2; 
} 
double m=fun(); 

我期待获得程序的输出为3.0,但它给了我输出为0,为什么?

它看起来像变量d2静态初始化?

不应该动态初始化它吗?

我已经在g ++ 4.8.1上测试过它,4.9.2 & MSVS 2010 &得到0作为输出。

+2

'它看起来像变量d2静态初始化?'排序。程序加载时,'d2'和'm'都会初始化为0。然后'd2'从'm'(它仍然是0)初始化。最后,'m'从'fun()'初始化。 –

+1

这是为什么?您正在打印'd2',而不是'm'。如果你有'int x = 0; int y = x; x = 42;'',你是否希望'y'被追溯设置为42? –

+0

[This answer](http://stackoverflow.com/a/22117407/1413133)将会有所帮助。 –

回答

3

C++文件中的变量从上到下进行初始化。所以md之后被初始化。

还有一些其他的微妙之处。

当编译器可以解决它时,它有时会发出变量的数据定义 - 将一个值设置为一个已知的常量。这些发生在程序加载之前。

然后,初始化的顺序是代码段 - 就像构造函数。这些段在编译单元中从上到下发生。

在你的情况下d=m我认为从m的槽中复制值。其中设置为0.0

然后调用m=fun(),复制具有正确值的插槽。

1

是的,d2m都具有静态存储持续时间,因为它们在命名空间范围内声明为未修饰。

这意味着它们是零初始化作为任何其他初始化发生之前的第一步。然后,d2设置为m。直到之后那个,那m变成了3.0

考虑下面的,基本上是同样的事情:

int main() 
{ 
    int x = 0, y = 0; 
    y = x; 
    x = 3; 
} 

显然,在这里,它是无稽之谈期待y等于3,但是这是你在做什么。

如果您预计的初始化会发生像函数-static变量,初始化发生在第一次使用(排序),您是错误的。

+0

@PravasiMeet:不,我不能证明一个否定。相反,你为什么不解释为什么这个简单的答案“仍然是错误的”,为什么你“不同意”? –

+0

@PravasiMeet:或者你不愿意,或者你早先说过要先放弃投票。这个答案只有一个,它仍然存在。 –

+1

@Pravasi:对,另一个证据表明,你没有删除你的失望,与你的说法相反。今天充满谎言:( –