1. 程式人生 > >extern "C" 用法理解與總結

extern "C" 用法理解與總結

被extern "C"修飾的變數和函式是按照C語言方式進行編譯和連結的

舉個例子:

1.moduleA、moduleB兩個模組

2.B呼叫A中的程式碼

3.其中A是用C語言實現的,而B是利用C++實現的

//moduleA標頭檔案:moduleA.h

#ifndef __MODULE_A_H
#define __MODULE_A_H
int fun(int, int);
#endif

//moduleA實現檔案:moduleA.c

#include"moduleA"
int fun(int a, int b)
{
return a+b;
}

//moduleB標頭檔案:moduleB.h

#idndef __MODULE_B_H
#define __MODULE_B_H

#ifdef __cplusplus //而這一部分就是告訴編譯器,如果定義了__cplusplus(即如果是cpp檔案, extern "C"{ //因為cpp檔案預設定義了該巨集),則採用C語言方式進行編譯
#include"moduleA.h"
#endif

… //其他程式碼

#ifdef __cplusplus
}
#endif

#endif

//moduleB實現檔案:moduleB.cpp

#include"moduleB.h"
int main()
{
cout<<fun(2,3)<<endl;
}

解釋:

1.moduleA實現檔案是用C實現的,所以函式編譯出來的符號是不帶形參型別的(因為C語言沒有過載,所以編譯出來符號只需要函式名唯一標識),如_fun

2.moduleB實現檔案是用CPP實現的,它中間使用了fun函式,預設情況下,int fun(int, int);編譯成了_fun_int_int這樣的符號,這個時候連結到目標檔案,就會找不到符號而報錯

3.如果讓int fun(int, int);在moduleB實現檔案中也編譯成_fun這樣的符號,就可以正常工作了。所以就需要在這個函式宣告的地方,用extern “C"標記,所以在moduleB的的標頭檔案中用extern ”C"標識

總結:

1. c檔案的原始碼編譯出來的函式符號是不帶形參的

2. c++中可能會連結到c原始碼編譯出來的目標檔案,這個時候需要C++中包含C函式宣告的時候用extern "C”指定,這樣C++原始碼編譯出來的C函式的符號也是按照C的規則,不帶形參的

這樣最終目標模組連結的時候,符號就能對應上