2016-02-23 54 views
0

在我的公司,我們正在開發一箇中型項目,我們計劃使用CMake作爲構建平臺生成器。在這種情況下,我和我的同事們正在討論應該使用CMake的方式。我們的討論達成了一個轉折點,我們必須決定使用的方法。我們的目錄結構與此類似:CMake在一箇中型項目中的最佳方式是什麼?

<"our project"> \ 
    modules \ 
     module_1 \ 
     tests \ 
      test_example.cpp 
     mock 
      some_mock_class.hpp 
     some_class.hpp 
     some_class.cpp 
     ... 
     module_2 \ 
     ... 
     module_3 \ 
     ... 
    utility \ 
     ... 

1 - 第一件事是先,我的同事認爲,像「SRC」和文件夾「包括」是C編程的提醒,並沒有發生在現代C++程序,所以我們不需要它們。所以我們將它們從結構中移除,但是成爲一名Linux員工;我不確定這是否是一個好主意。我們是否應該爲頭文件設置一個「include」目錄,以便CMake可以將它們適當地安裝到安裝目標的include目錄中;或者CMake可以適當地處理它們?我們是否應該爲包含並定義所有目標的項目根目錄創建一個CMakeLists.txt,或者我們應該爲每個模塊創建一個CMakeLists.txt,然後使用「add_subdirectory」指令來包含它們?我的同事認爲CMakeLists.txt是最好的,因爲這種模塊實現者完全不需要考慮CMake,而且一兩個管理員可以維護文件;但我認爲每個模塊實現者都更加意識到他們使用哪些庫,以及如何編譯他們的模塊 - 他不同意這一點。你在這種情況下建議什麼?

如果您之前(或知道案例)之前確實使用CMake做過這樣一箇中等規模的項目,請您推薦我們他們做了什麼,如果可能的話,爲什麼?

真誠

+1

只有一點你的觀點:每個模塊/目標一個'CMakeLists.txt'是正確的決定。根據我的經驗,模塊的實現者不需要深入瞭解CMake。 CMake非常簡單,實現者通常會從其他模塊之一複製一個「CMakeLists.txt」模板並更改一些屬性。管理員可以提供更先進的指導,例如如果其中一個模塊需要特殊處理。當項目變得越來越大時,您可能會考慮將經常使用的功能放入CMake宏/函數包裝器中。 – Florian

+0

你可以禮貌地問你的同事看看CMake是另一種編程語言,例如, [模塊化編程](https://en.wikipedia.org/wiki/Modular_programming)是一個好主意(正如你用C++代碼所做的那樣)並將所有東西放到一個源文件中可能是件壞事。 – Florian

+0

他將那些CMakeLists.txt文件稱爲「垃圾」,並說「他不想在我們的源代碼中看到這些垃圾」......所以,我不知道他是否可以客觀接受你的觀點:) TBH ;我是「每個模塊一個」方法的專家。它似乎更容易維護,但我想了解說服別人的好例子;) –

回答

0

該主題是巨大的,但總之我個人的建議。對於一箇中間項目我應該已經應用了一個組件模型。那麼合理的是,要有帶有CMakeLists.txt的組件目錄,這些CMakeLists.txt通過add_subdirectory()由頂層CMakeLists.txt引用。每個組件 - 一個單獨的庫(我喜歡靜態的)。

對於組件文件夾,我覺得合理的做法是隱藏private子目錄下的所有內部內容(即實現和私有頭文件...),以免暴露給外部。然後,在頂級組件目錄中,您只有標題供其他人使用。在私人目錄中,您可以混合使用來源和標題 - 這僅僅是中期項目品味的問題。如果組件很大,私人目錄也可以被分解。但是,您需要決定是將所有工件添加到該組件的單個CMakeLists.txt中,還是要具有子庫。但在這種情況下,用戶應單獨鏈接到它們,而不是僅鏈接到組件的庫。

在最好的情況下,該文件夾結構應遵循的依賴性結構並形成樹視圖構建系統,其中,所述部件具有作爲關於其它組分儘可能少內部knowlege。在這種情況下,如果可能存在重構,您將具有良好的可配置性和靈活性。換句話說,構建系統的設計在我看來類似於C++中的類設計 - 相同的原則。

運行cmake的真實(目標)構建目錄可以位於任何位置,通常位於源目錄之外。如果你有足夠的內存,一個好的地方可能是RAM盤。那麼對於乾淨的構建,你只需要刪除它,就是這樣。但是源代碼和構建本身不依賴於它的位置。

啊,是的,還有一個提示。我的建議是從組件目錄(如#include "SomeHeader.hpp",位於ComponentX/SomeHeader.hpp)開始的路徑中包含標題。然後CMakelists.txt用於執行組件已知的ComponentX目錄。這意味着,頭文件的路徑在源文件中不會被硬編碼。這帶來了一些限制,如獨特的文件名稱,但更容易更改組件的位置。

希望這有助於。

+0

當我們使用「include/ComponentX /」文件夾來保留我們的頭文件並相應地配置CMakeLists.txt時,最後一個限制是驅動器;這樣我們的圖書館就不會與系統的圖書館發生衝突 - 在名稱衝突的情況下。但是現在,我不知道該怎麼做,因爲我的同事的動機讓我困惑。這就是我爲什麼要問SO社區的原因。 –

+0

是的......有一段時間我得出的結論是,在大多數情況下,集中cmake上的所有依賴關係(外部路徑解析和鏈接)是非常方便的,而不是在代碼級別上。您也可以在包含的源代碼中硬編碼整個路徑。但是在這種情況下,依賴關係通常會相乘,因爲cmake在大多數情況下已經用於依賴關係,比如位於非標準路徑中的系統或第三方庫。所以,我雖然爲什麼代碼應該關心這一點。 – dmi

相關問題