動態鏈接DLL與靜態鏈接LIB

背景

動態鏈接與靜態鏈接一直以爲很清楚,後來遇到bug才知道自己不是很清楚!

靜態鏈接

靜態庫(.lib):函數和數據被編譯進一個二進制文件(通常擴展名爲.LIB)。在使用靜態庫的情況下,在編譯鏈接可執行文件時,鏈接器從庫中複製這些函數和數據並把它們和應用程序的其他模塊組合起來創建最終的可執行文件(.EXE文件)。當發佈產品時,只需要發佈這個可執行文件,並不需要發佈被使用的靜態庫。

動態鏈接

動態庫(.lib文件和.dll文件):在使用動態庫的時候,往往提供兩個文件:一個引入庫(.lib)文件(也稱“導入庫文件”)和一個DLL(.dll)文件。雖然引入庫的後綴名也是“lib”,但是,動態庫的引入庫文件和靜態庫文件有着本質的區別,對一個DLL文件來說,其引入庫文件(.lib)包含該DLL導出的函數和變量的符號名,而.dll文件包含該DLL實際的函數和數據。在使用動態庫的情況下,在編譯鏈接可執行文件時,只需要鏈接該DLL的引入庫文件,該DLL中的函數代碼和數據並不可複製到可執行文件,直到可執行程序運行時,纔去加載所需的DLL,將該DLL映射到進程的地址空間中,然後訪問DLL中導出的函數。這時,在發佈產品時,除了發佈可執行文件以外,同時還需要發佈該程序將要調用的動態鏈接庫。

例子

以opencv2.4.13爲例來說明,下圖是opencv的動態庫和靜態庫的目錄:

opencv的庫目錄

bin文件夾下放的是.dll文件,lib文件夾下放的是.lib文件;staticlib文件夾下放的是也.lib文件
但是lib文件夾下的是動態鏈接的引入庫(.lib)文件,staticlib文件夾下放的是靜態鏈接的二進制文件(.lib)。

同時可以看到staticlib文件夾下的.lib文件比lib文件夾下的.lib文件大很多,這是因爲靜態鏈接的二進制文件(.lib)包含實際執行代碼、符號表等等(較大),動態鏈接的引入庫文件(.lib)包含該DLL導出的函數和變量的符號名(較小)。

staticlib文件夾下的.lib文件
lib文件夾下的calib3d2413.lib

同時注意:靜態庫(.lib)和動態庫(.lib文件和.dll文件)都debug和release之分。

參考

VC++深入詳解(孫鑫修訂版)
http://www.cppblog.com/amazon/archive/2009/09/04/95318.html
http://blog.sina.com.cn/s/blog_6dd65c6f0100vveq.html

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章