每日一问3: C++中extern关键字的作用
//fileA.cpp int i; //声明并定义i int j = 1; //声明并定义j double max(double d1,double d2){} //定义 //fileB.cpp extern int i; //声明i而非定义 extern int j = 2; //定义j而非声明,会报错,多重定义 int j; //错误,重定义,注意这里的j是在全局范围内声明 extern double max(double d1,double d2); //声明
- external,外部链接属性。非常量全局变量和自由函数(除成员函数以外的函数)均默认为外部链接的,它们具有全局可见性,在全局范围不允许重名,详情可见例子。
- internal,内部链接属性。具有该属性的类型有,const对象,constexpr对象,命令空间内的静态对象(static objects in namespace scope)
- none,在类中、函数体和代码块中声明的变量默认是具有none链接属性。它和internal一样只在当前作用域可见。
//fileA.cpp int i = 1; //声明并定义全局变量i //fileB.cpp extern int i; //声明i,链接全局变量 //fileC.cpp extern int i = 2; //错误,多重定义 int i; //错误,这是一个定义,导致多重定义 main() { extern int i; //正确 int i = 5; //正确,新的局部变量i; }
//fileA.cpp extern const int i = 1; //定义 //fileB.cpp //声明 extern const int i;
// 声明printf函数使用C链接 extern "C" int printf(const char *fmt, ...); //声明指定的头文件内所有的东西都使用 C 链接 extern "C" { #include <stdio.h> } // 声明函数ShowChar和GetChar使用 C 链接 extern "C" { char ShowChar(char ch); char GetChar(void); } // 定义函数 ShowChar 和 GetChar 使用 C 链接 extern "C" char ShowChar(char ch) { putchar(ch); return ch; } extern "C" char GetChar(void) { char ch; ch = getchar(); return ch; } // 声明全局变量 errno 为C链接 extern "C" int errno; //又比如,在程序中常见的代码段 #ifdef __cplusplus extern "C" { #endif /**** some declaration or so *****/ #ifdef __cplusplus } #endif //这里__cplusplus是cpp中的自定义宏,定义了这个宏就表明这是一段cpp的代码,也就是说,
//上面的代码的含义是:如果这是一段cpp的代码,那么加入extern "C"{和}处理其中的代码。
- 使用extern和包含头文件来引用函数有什么区别呢?
与include相比,extern引用另一个文件的范围小,include可以引用另一个文件的全部内容。extern的引用方式比包含头文件要更简洁。extern的使用方法是直接了当的,想引用哪个函数就用extern声明哪个函数。这样做的一个明显的好处是,会加速程序的编译(确切的说是预处理)的过程,节省时间。在大型C程序编译过程中,这种差异是非常明显的。
参考博客: