2015-08-12 2 views
41

У меня есть структура каталогов для моего кода C++, который идет как это:В чем разница между include_directories и target_include_directories в CMake?

| 
|->include 
|->src 

Я пишу файл CMakeLists.txt для моего кода. Я хочу понять разницу между include_directories и target_include_directories в CMake.

В чем разница между их использованием и добавлением моего пути к файлу include, который я должен использовать?

+3

Вы прочитали документацию для ['include_directories'] (http://www.cmake.org/cmake/help/v3.2/command/include_directories.html) и [' target_include_directories'] (http: //www.cmake.org/cmake/help/v3.2/command/target_include_directories.html)? Что вы не понимаете в разнице между ними? –

+24

В документации нет ясности. Я прочитал его и догадался, что написал Анджей в своем ответе, но нет описаний, примеров и системы, предназначенной для построения проекта. В документации CMake нет примеров, основанных на проектах. Если бы была хорошая и исчерпывающая документация CMake, я бы не стал обременять сообщество этими вопросами. –

ответ

50

include_directories(x/y) влияет на область действия каталога. Все цели в этом CMakeList, а также во всех подкаталогах, добавленных после точки его вызова, будут иметь путь x/y, добавленный в свой путь include.

target_include_directories(t x/y) имеет целевую область — добавляет x/y к пути включения цели t.

Вы хотите, чтобы бывший, если все ваши цели используют включенные каталоги, о которых идет речь. Вы хотите, чтобы последний, если путь определен для цели, или если вы хотите более тонкое управление видимостью пути. Последнее исходит из того факта, что target_include_directories() поддерживает квалификаторы PRIVATE, PUBLIC и INTERFACE.

+19

Я думаю, что последнее должно быть предпочтительным (пока используется cmake 3). Он имеет дополнительное преимущество: «x/y» в пути включения любых зависимых целей, которые используют '' t'' в своих командах '' target_link_libraries''. Конечно, есть место для первого, но я считаю, что последнее, как правило, лучше. – Phil

+1

Исходный ответ показал, что будут затронуты только цели и поддиры, добавленные после 'include_directories'. Я редактирую ответ: в документации четко указано, что затронуты * все * цели в текущих CMakeLists.Документация не упоминается, но затронуты только поддиры после вызова (как было правильно указано в исходном ответе) –

+0

@Phil, 'target_include_directories' был введен в CMake 2.8.11 (май 2013) –

16

Кроме того, что правильно говорит Angew's answer, еще одна очень важная разница между include_directories и target_include_directories является то, что при использовании PUBLIC или INTERFACE, последний заселить INTERFACE_INCLUDE_DIRECTORIES свойство мишени. Это свойство полезно, когда другая цель использует target_link_libraries для ссылки на исходную цель, так как целевая ссылка будет автоматически включаться в каталоги. См. example.

Эта важная особенность очень хорошо скрыта в документации: target_include_directories упоминания заселение INTERFACE_INCLUDE_DIRECTORIES, которого documentation говорит:

Когда целевые зависимости определяется с помощью target_link_libraries(), CMake прочтет это свойство всех целевых зависимостей в определить свойства сборки потребителя.

Смежные вопросы