在不同的翻译单元中启动全局变量(涉及链接)



我最近正在审查C 。这是我的问题。请参阅file1.cppfile2.cpp中的代码。

file1.cpp

int x1 = 1;
int y1 = x1 + 2;

file2.cpp

#include "necessary_headers"
extern int y1;
int y2 = y1 + 2;
int main()
{
    cout << "y2 is "<<y2<<endl;
    return 0;
}

我按不同的顺序编译:

gcc file1.cpp file2.cpp

当然是y2 is 5的输出。

gcc file2.cpp file1.cpp 

输出为 y2 is 2。(我的问题是关于这个(

我也尝试以下方法:gcc file2.cpp。当然,这给出了undefined reference to y1

我的问题是,即使链接序列是"错误",gcc file2.cpp file1.cpp为什么会编译而不是给出undefined reference to y1错误?是因为当链接file2.cpp链接时,链接器很聪明以引用以下文件file1.cpp中定义的y1?这样,y1file2.cpp中初始化为0(默认值(,而不是在file1.cpp中使用定义?因此,通过这种方式,file1.cpp "int y1 = x1 + 2"中的定义和初始化不是由链接序列无效吗?如果没有,我该如何执行该语句以分配y1 = x1 + 2?最后,这是一般的编译器行为吗?根据C 标准,在不同翻译单元中初始化全局变量的顺序不确定。

感谢您的帮助!真的很感激。

我的问题是,为什么gcc file2.cpp file1.cpp编译而不是编译 即使链接序列为 "错误"?

来自basic.link#2.1

当名称具有外部链接时,它表示的实体可以是 由其他翻译单元范围的名称提及 同一翻译单元的其他范围。

因此,如果您编译了包含 y1的定义的文件(例如file1.cpp(,则extern int y1;不确定。

对于链接期间,从其他翻译单元中检查了y1的定义。

最新更新