Qual è la differenza tra include_directories e target_include_directories in CMake?


134

Ho una struttura di directory per il mio codice C ++ che va così:

|
|->include
|->src

Sto scrivendo un file CMakeLists.txt per il mio codice. Voglio capire la differenza tra include_directoriese target_include_directoriesin CMake.

Qual è la differenza tra il loro utilizzo e per aggiungere il mio percorso del file include quale dovrei usare?


4
Hai letto la documentazione per include_directoriese target_include_directories? Cosa non capisci della differenza tra loro?
Qualcuno programmatore,

74
Non c'è chiarezza nella documentazione. L'ho letto e ho ipotizzato ciò che Angew ha scritto nella sua risposta, ma non ci sono descrizioni, né esempi e per un sistema destinato alla costruzione di progetti, non ci sono esempi basati sul progetto nella documentazione di CMake. Se ci fosse stata una buona ed esauriente documentazione di CMake, non avrei gravato sulla comunità con queste domande.
Ujjwal Aryan,

I concetti di cmake sono scarsamente documentati. Particolarmente mirato e "non mirato".
John Greene,

Risposte:


148

include_directories(x/y)influisce sull'ambito della directory. Tutti i target in questa CMakeList, così come quelli in tutte le sottodirectory aggiunti dopo il punto della sua chiamata, avranno il percorso x/yaggiunto al loro percorso include.

target_include_directories(t x/y)ha un ambito target: si aggiunge x/yal percorso include per target t.

Vuoi il primo se tutti i tuoi target usano le directory include in questione. Si desidera quest'ultimo se il percorso è specifico per un target o se si desidera un controllo più preciso della visibilità del percorso. Quest'ultimo deriva dal fatto che target_include_directories()supporta i PRIVATE, PUBLICe INTERFACEqualificazioni.


35
Penso che quest'ultimo dovrebbe generalmente essere preferito (purché si usi cmake 3). Ha l'ulteriore vantaggio di inserire x/yil percorso di inclusione di tutti gli obiettivi dipendenti che usano tnei loro target_link_librariescomandi. Naturalmente c'è un posto per il primo, ma credo che il secondo sia generalmente migliore.
Phil

2
La risposta originale affermava che include_directoriessaranno interessati solo i target e i sottodiretti aggiunti dopo . Sto modificando la risposta: la documentazione afferma chiaramente che sono interessati tutti gli obiettivi nelle attuali CMakeList. La documentazione non menziona ma sono interessati solo i sottodiretti dopo la chiamata (come è stato correttamente affermato nella risposta originale)
tamas.kenez,

@Phil, target_include_directoriesè stato introdotto in CMake 2.8.11 (maggio 2013)
tamas.kenez il

@ tamas.kenez Grazie per avermi portato alla mia attenzione, risolto. Ero abbastanza convinto che fosse una cosa "d'ora in poi".
Angew non è più orgoglioso di SO

40

Accanto a ciò che dice correttamente la risposta di Angew , un'altra differenza molto importante tra include_directoriese target_include_directoriesè che, se usato con PUBLICo INTERFACE, quest'ultimo popola la INTERFACE_INCLUDE_DIRECTORIESproprietà del bersaglio. Questa proprietà è utile quando un'altra destinazione utilizza target_link_librariesper collegarsi alla destinazione originale, poiché alla destinazione di collegamento verranno automaticamente aggiunte quelle che includono le directory. Vedi esempio .

Questa importante funzionalità è piuttosto ben nascosta nella documentazione: target_include_directories menziona il popolamento INTERFACE_INCLUDE_DIRECTORIES, la cui documentazione dice:

Quando le dipendenze di destinazione vengono specificate utilizzando target_link_libraries () , CMake leggerà questa proprietà da tutte le dipendenze di destinazione per determinare le proprietà di generazione del consumatore.


Questa è la prima volta che leggo una spiegazione comprensibile delle PUBLICproprietà ecc.! Grazie: D
RL-S il

2

Come ha detto @Angew, la differenza è:

1, include_directories () è accessibile per tutti i file nell'albero dei sorgenti 2, target_include_directories () è accessibile solo per una destinazione specifica durante la compilazione.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.