extern "C" 一句话概括 extern "C" 的作用:告诉 C++ 编译器,编译某段代码时不要进行名字重整,以此达到 C++ 中调用 C 函数,或者 C 中调用 C++ 函数的目的; 之所以 C++ 会有名字重整,是因为 C++ 为了实现重载等特性,需要在编译期把函数名重整,针对不同的参数调用识别不同的函数名; 注意:extern "C" 是 C++ 为了兼容 C 代码才加上的东西,只在 C++ 里才有, C 语言里面是没有 extern "C" 的; C模块: 不会有名字重整,编译后,声明的函数名都没变: void foo(void) --> foo C++模块: 存在名字重整:编译后,声明的函数名会改变: void foo(void) --> xxxfooxxx C 模块中调用 C++ 函数: 两个模块分别编译,链接期 C 模块按照未重整的名字 foo 去 C++ 模块的 .obj 文件里查找函数,会失败! C++ 模块中调用 C 函数: 两个模块分别编译,链接期 C++ 模块按照重整后的名字 xxxfooxxx 去 C 模块的 .obj 文件里查找函数,会失败! C++ 为了兼容 C 代码,加上了 extern "C"。 C++ 中调用 C 模块的函数: main.cpp: extern "C"{ #include "CClass.h" }; int _tmain(int argc, _TCHAR* argv[]) { foo(); return 0; } CClass.h 是C模块的头文件,以上代码告诉编译器, CClass.h 里面的函数声明,不要进行名字重整。这样 main.cpp 在编译的时候, CClass.h 里面的函数不会进行名字重整,C++ 模块可以 从中找到正确的函数; 如果不加 extern "C" 就会出现链接错误:error LNK2001: 无法解析的外部符号 "void __cdecl foo(void)" (?foo@@YAXXZ) C++ 提供接口给 C 模块调用: cppclass.h: extern "C" void foo(void); extern "C" void func(int); main.c extern void foo(void); extern void func(int); cppclass.h 是 C++ 模块的头文件,以上代码告诉编译器,foo,func 这两个函数,不要jinx那个名字重整。这样 cppclass 在编译的时候, foo,func 不会被重整, C 模块可以从中找到正确 的函数。 这种情况下,因为在 C 中 extern "C" 是不合法的,所以不能直接在 main.c 中 #include "cppclass.h", 而是通过 extern void foo(void); 的方式声明 foo 这个函数,链接的时候会从 cppclass.obj 里找到它。 DLL 的头文件中使用 extern "C": 在 DLL 中,如果我们用 C++ 编译器编译它而且没有加上 extern "C",那么就有可能这个 dll 不能被 C 模块调用,因为其中的函数被重整了。 为了让这个 dll 能够被 C 模块调用,我们需要为它加上 extern "C",下面的头文件可以被 C 模块或 C++ 模块包含使用。 // MyCFuncs.h #ifdef __cplusplus extern "C" { // only need to export C interface if // used by C++ source code #endif __declspec( dllimport ) void MyCFunc(); __declspec( dllimport ) void AnotherCFunc(); #ifdef __cplusplus } #endif
参考链接:
http://www.cnblogs.com/graphics/archive/2010/12/24/1916343.html