Are there any drawbacks to declaring variables in header files without the “extern” keyword?
我最近开始意识到,"extern"关键字的使用受到了极大的鼓励。因此,我开始怀疑当前(无外部)使用头文件的方式是否有任何问题:
主要内容:
1 2 3 4 5 6 7 8 9 | #include"main.h" #include"function.h" int main(void){ globalvariable = 0; testfunction(); return 0; } |
H.
1 2 3 4 5 6 | #ifndef MAIN_H_ #define MAIN_H_ int globalvariable; #endif /* MAIN_H_ */ |
C函数:
1 2 3 4 5 6 7 | #include"main.h" #include"function.h" void testfunction(){ globalvariable++; return; } |
函数:
1 2 3 4 5 6 | #ifndef FUNCTION_H_ #define FUNCTION_H_ void testfunction(void); #endif /* FUNCTION_H_ */ |
因此,每个需要访问globalvariable的新源文件只需要包含main.h。
此方法的一个明显缺点是数组:声明数组后,不能使用element0、element1,…格式将值分配给数组。
顺便问一下,当我给globalvariable一个初始值为零时,我是否定义了它?或者内存分配更早?
另外,我使用的方法有官方术语吗?
对于您使用的方法,我知道的唯一官方术语是"依赖于实现的行为"。一旦开始使用不同的编译器(甚至可能是同一个编译器的不同版本)进行构建,该方法就会遇到各种各样的问题。有些人会抛出一个链接器错误,但有些人会接受它(尽管没有确切的保证如何解释它)。我强烈建议您采用一种更标准的方法,编译器将以可预测的方式进行解释。
变量的定义必须在.c文件中。如果要从另一个.c文件访问该变量,请在头中添加一个
要回答您的分配问题,在程序开始运行之前,将为所有全局分配内存。全局变量占用空间,即使它只用于从不运行的代码的一部分。你的
1 | extern int globalvariable; |
是一个声明
1 | int globalvariable; |
是一个声明和一个暂定的定义。
在C语言中,同一个变量有多个定义是非法的,如果在包含在多个翻译单元中的头文件中使用后者,就会发生这种情况。
然而,UNIX系统历史上允许这种用法,所以大多数编译器将接受代码,尽管它是无效的C。
问题在于,当您试图链接程序时,可能会由于多个定义而导致链接错误。您取决于这里实现定义的行为——允许实现将重复定义视为所有引用单个对象的定义,但不需要这样做。
您的代码的缺点是,您可能会遇到链接器错误。1
>1。其中"可能"是基于在一组不同的工具链上构建代码的概念。
ANSI C标准规定
If the declaration of an identifier for an object has file scope and
no storage-class specifier, its linkage is external.