建構系統、函式庫與相依性

CMake 與外置建構(out-of-source build)

/ SEE-mayk /

手寫一份 Makefile 在單一機器上行得通,但只要你希望程式能在 Linux、macOS 與 Windows 上、用不同編譯器與函式庫位置建出來,手寫的 Makefile 就會變成一場充滿特例的噩夢。CMake 是一個位於上一層的工具:你不直接寫建構流程,而是用一個可移植的檔案(CMakeLists.txt)把專案描述一次,CMake 再替你所在的系統產生實際的建構檔。

這就是為什麼它被稱為後設建構系統或建構產生器:CMake 本身並不編譯你的程式碼。你執行 cmake,它檢視你的機器(有哪個編譯器、函式庫在哪裡),然後寫出一份真正的原生建構,例如 Unix Makefiles 或一個 Visual Studio 專案;接著你執行那份建構去做真正的編譯。CMake 也強烈鼓勵外置建構:與其把產生的檔案(目的檔、可執行檔、快取檔)散落在你的原始碼之間,你另建一個獨立的 build 目錄並在那裡執行建構,於是你的原始碼樹保持乾淨,而且你可以整個刪掉 build 目錄重新開始。

為什麼重要:CMake(以及 Meson 之類的類似工具)正是大多數大型跨平台 C 與 C++ 專案得以用一份描述就在各處都建得起來的方式。代價是一條學習曲線與多一層間接:當出問題時,你現在面對的可能是 CMake 的問題或產生出來的建構的問題,而它的腳本語言本身又是另一樣要學的東西。但對任何打算讓別人也能建構的專案來說,那份可移植性通常都值得。

$ mkdir build && cd build # 一個獨立的 build 目錄 $ cmake .. # 產生原生建構 $ cmake --build . # 執行它來編譯 rm -rf build/ 一次丟掉所有產生的檔案。

CMake 把原生建構產生到一個獨立目錄;外置建構讓原始碼樹保持乾淨。

CMake 產生一份建構;它並不取代 Make 或編譯器,而是去驅動它們。一個常見的誤解是以為光跑 cmake 就會產出程式——你之後仍得執行產生出來的建構(或 cmake --build)才真正完成編譯。

又稱
meta-build systembuild generator後設建構系統建構產生器