legacy
參考最近在看專案**,經常看到header file中,開頭:
中間包裹:#ifdef __cplusplus
extern
"c"#endif
/* __cplusplus */
includes
,typedefs
,以及function prototypes
。
不懂就要問,去查了下,發現這是為了告知編譯器,以c語言的方式編譯**。extern "c"
表示編譯生成的內部符號名使用c約定。
不過在stackoverflow上有人提問了幾個挺好的問題。3
如果c++標頭檔案a.hh,include 乙個c標頭檔案b.h,b.h中include c.h,這是如何工作的?提問者認為:編譯器進入b.h時,__cplusplus
已經定義過了,所以會包裹上extern "c"
,這樣就相當於取消定義了__cplusplus
,但是進入c.h時,這些將不會被包裹入extern "c"
。
【答】__cplusplus
仍存在於extern "c"
塊中,但是不影響。
extern "c" }
這樣的**是錯誤的嗎? 第二個extern "c"
做了什麼?
【答】巢狀使用是可以的。__cplusplus
在使用c++編譯器時是定義在每乙個編譯單元的。通常,這意味著__cplusplus
存在於.cpp檔案和任何被.cpp檔案include的檔案。如果不同的編譯但與包含了同乙個.h/.hh/.hpp檔案可以,那麼在不同時期它們會被解釋為c或c++**。如果你想.**件中的原型被解譯為c的符號(symbols),那麼它們應該在c中沒有extern "c"
,在c++中則有extern "c"
,所以需要#ifdef __cplusplus
檢查。
我們只是使用在了.**件中,而非.c檔案中。那麼如果乙個沒有原型的函式會被編譯器認為是c++的函式嗎?
【答】.cpp檔案中,沒有原型並且不在extern "c"
塊中的函式,將會由c++鏈結。因為它們沒有原型,它們只能在本檔案中呼叫,通常你也無須關心鏈結過程,所以這就可以了。
提問者也在使用一些第三方的c**,並且沒有使用extern "c"
包裹,那麼每次include乙個標頭檔案,都自己使用extern "c"
包裹起來是正確的處理方式嗎?
【答】你的處理方法是正確的。include乙個需要c鏈結過程的標頭檔案,你必須使用extern "c"
包含這個標頭檔案,這樣你才能和庫檔案鏈結。
最後,混合使用c和c++還需要注意什麼?
【答】沒什麼了。可以這樣混合使用c和c++。
當我們想從c++中呼叫c的庫時,不能僅僅說明是乙個外部函式,因為呼叫c函式的編譯**和呼叫c++函式的編譯**是不同的。如果你僅說明乙個外部函式, c++編譯器假定它是c++的函式,編譯成功了,但當你連線時會發現錯誤。解決的方法就是指定它為c函式:
指定一群函式的話:extern
"c"// 後跟函式描述
如果想c和c++混用的話:extern
"c"
參考11#ifdef __cplusplus
extern
"c"#endif
認為上述方式在header file中太醜陋了,所以它推薦把extern "c"
用在.cpp檔案中。
這樣不會在.**件**現多次巢狀,影響美觀。。。而且不會出現忘記包裹而出現鏈結錯誤。
extern
"c"int
main()
這兩個是我還沒看呢。
include c hdrs system | standard c++
call a c function from c++ code
calling c code from c++ with 『extern 「c」『
↩︎↩︎
c++中的name mangling↩︎
combining c++ and c - how does #ifdef __cplusplus work?↩︎
c和c 混合使用
我們編寫 經常需要c和c 混合使用,為了使 c 和 c 保持互相相容的過程呼叫介面,需要,為了簡化,從而定義了兩個巨集方面我們使用 1.在 c 裡加上 extern c 作為符號宣告的一部分。2.begin decls 和 end decls 在c語言 中標頭檔案中,充斥著下面的 片段 begin ...
C 和C 混合程式設計
由於歷史原因,很多時候我們的 並不完全是使用.net寫成的。這時候和以往c 的混合程式設計就顯得相當重要了。最近碰到了這樣的問題,將方法簡要記述如下。要在c 中呼叫c 函式,大體的思路是這樣的 首先將c 函式寫成dll形式的庫,然後在c 中匯入dll中的函式進行呼叫。具體的 類似這樣 c 1int ...
C和C 混合呼叫
extern c char strcpy char const char 注意它與下面的宣告的不同之處 extern char strcpy char const char 下面的這個宣告僅表示在連線的時候呼叫strcpy extern c 指令非常有用,因為c和c 的近親關係。注意 extern ...