变量的外部和外部"C"
extern and extern "C" for variables
我正在写一个c++共享库供C程序使用。但是,我有一个关于extern
和extern "C"
的问题。
考虑下面的代码
头文件是这样的:
#ifdef __cplusplus
extern "C" int global;
extern "C" int addnumbers(int a, int b);
#else
extern int global;
#endif
这工作得很好;我只需要声明
int global;
在我的。cpp或。c文件。然而,我不明白的是:
这里extern "C"
和extern
有什么区别?我试着评论extern "C" int global
,它工作!为什么?
我知道extern "C"
是用来做C联动的。这就是为什么我有extern "C" int addnumbers(int,int)
。换句话说,如果我想写一个c++函数,要在C程序中使用,我写extern "C"
。那么,全局变量呢?我想这里的情况有所不同?我希望C程序使用一个名为global
的c++变量,但我可以使用extern
而不是extern "C"
。为什么呢?这对我来说并不直观。
注释:我不认为这是重复的,因为我问的是当你将它用于变量和函数时有什么区别
通过将extern "C"
附加到您的c++声明(对象和函数一样)中,您赋予它们"C链接" -使它们可以从C代码中访问。如果省略这个"语言链接"规范,编译器就不会做任何努力来进行适当的链接。在函数的情况下,由于混淆,这将导致链接失败。对于全局变量,一切都可以正常工作,因为变量不需要修改。
然而,在我的系统(MS Visual Studio)上,如果我"忘记"在c++头文件中指定extern "C"
链接规范,C和c++之间的链接就不起作用了。错误信息示例:
error LNK2001: unresolved external symbol "int global" (?_global)
然而,当我用dumpbin
实用程序检查包含global
定义的编译后的c++源代码时,我看到
00B 00000014 SECT4 notype External | ?global@@3HA (int global)
所以MS Visual Studio修改了全局变量的名称,除非它们有C链接——这使得C链接规范是强制性的。
另外,考虑下面的例子:
namespace example {
int global;
}
如果全局变量在命名空间内,C代码将无法访问它。在这种情况下,所有编译器都需要在c++声明中使用适当的链接规范:
namespace example {
extern "C" int global;
}
结论:
使用extern "C"
当你想要C链接-不管它是一个函数还是一个全局变量。如果它是一个全局变量,它可能会工作,但它不能保证(并且可能是危险的)。
extern
只是告诉编译器下一个变量(global)可能还没有被声明,但它在另一个翻译单元中被声明为global,并且在链接阶段,符号"global"将与内存中的一个区域相关联。
虽然extern "C"
是,正如一些人评论的那样,用于解决c++中的名称混淆问题,但该函数将被链接器称为addnumbers_i_i
(或类似的东西),而在C中它的符号是addnumbers
" c++有一个特殊的关键字来声明带有C绑定的函数:extern "C"。声明为extern "C"的函数使用函数名作为符号名,就像C函数一样。因此,只有非成员函数可以声明为外部"C",并且它们不能被重载。"
对于编译器生成的函数名,c++中没有标准。关键字extern "C"指示编译器在C标准中生成函数名
我发现extern "C"是用来使c++函数在C标准中编译的,它不与变量有关,因为C和c++中函数名称的解决方案不同。如"void foo(int x, int y)", C编译器会将其翻译为"_foo",而c++编译器会将其翻译为"_foo_int_int"。
- 如果全局变量默认是外部变量,为什么要添加"extern"关键字?
- 堆栈/帧指针作为外部变量
- const_cast const 方法中的"this"将"this"分配给外部变量?
- 外部变量的初始化
- 如何在命名空间中初始化外部变量
- 将全局外部变量的私有版本与 OpenMP 结合使用
- 使用外部变量会导致"unsigned char"错误LNK2001
- 为什么通过复制捕获 lambda 具有与外部变量相同的地址
- 我们是否应该在项目中包含的所有文件中声明外部变量
- 如何将 Wifi.localIP() 转换为字符串并将其存储到外部变量
- 具有仅在某些情况下引用外部变量的属性的类
- C 中的外部变量
- Xcode C++外部变量链接器错误
- 使用外部变量时的多重定义错误
- C 和 C++ 中的外部变量有什么区别
- 默认情况下,非常量变量不被视为外部变量吗?
- 当外部变量在其他文件中声明不同时,如何使G 产生警告
- 是初始化为其默认值的外部变量
- 将外部变量传递给类 c++
- C++中有更多的类和外部变量