C++ Cmake include_directories()

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/19981534/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-27 23:18:46  来源:igfitidea点击:

Cmake include_directories()

c++includecmake

提问by memecs

This is my project tree:

这是我的项目树:

project
| + src
| + external
| | + foo
| | | + include
| | | | - foo.hpp
| | | + src
| | | | - foo.cpp
| | | | - CMakeLists.txt
| | | - CMakeLists.txt 
| | + CMakeLists.txt 
| + src
| | - main.cpp
| - CMakeLists.txt

foo.cpp includes foo.hpp:

foo.cpp 包括 foo.hpp:

// foo.cpp
#include "foo.hpp"

Now the problem is that including the directory in the top CMake successfully find foo.hpp, but if I include in the subproject it doesn't. Any reason for it? (directories are included before the executable is compiled).

现在的问题是,在顶级 CMake 中包含目录成功找到 foo.hpp,但如果我包含在子项目中,则不会。有什么理由吗?(在编译可执行文件之前包含目录)。

// project/CMakeLists.txt
include_directories(external/foo/include) //OK
add_subdirectory(external)

add_executable(main main.cpp)
target_link_libraries(main foo)

// project/external/CMakeLists.txt
add_subdirectory(foo)

// project/external/foo/CMakeLists.txt 
include_directories(include) // NOT WORKING
add_subdirectory(src)

// project/external/foo/src/CMakeLists.txt 
add_library(foo foo.cpp)

回答by ComicSansMS

Quoting the documentation for include_directories:

引用文档include_directories

The include directories are added to the directory property INCLUDE_DIRECTORIES for the current CMakeLists file. They are also added to the target property INCLUDE_DIRECTORIES for each target in the current CMakeLists file. The target property values are the ones used by the generators.

包含目录被添加到当前 CMakeLists 文件的目录属性 INCLUDE_DIRECTORIES。它们还会添加到当前 CMakeLists 文件中每个目标的目标属性 INCLUDE_DIRECTORIES。目标属性值是生成器使用的值。

The INCLUDE_DIRECTORIESdirectory propertyis inherited to all subdirectories and all targets in the directory.

INCLUDE_DIRECTORIES目录属性继承目录中的所有子目录和所有目标。

  • Specifying ${CMAKE_CURRENT_SOURCE_DIR}for include_directoriesis redundant as relative paths are interpreted as relative to this directory by default. You should throw it out to increase readability.
  • Specifying an include directory in both a subdirectory and its parent is redundant. You should avoid this and settle on one location.
  • Use get_propertyand messageto double-check that all directories and targets end up with the correct entries in their INCLUDE_DIRECTORIESproperty.
  • If you are free to require CMake 2.8.11 as a minimum requirement, consider abandoning include_directoriescompletely and use target_include_directoriesinstead. This has the advantage that include dependencies get resolved on a per-target basis exclusively which is usually the more desirable behavior.
  • 指定${CMAKE_CURRENT_SOURCE_DIR}forinclude_directories是多余的,因为默认情况下相对路径被解释为相对于该目录。你应该把它扔掉以增加可读性。
  • 在子目录及其父目录中指定包含目录是多余的。您应该避免这种情况并选择一个位置。
  • 使用get_propertymessage仔细检查所有目录和目标是否在其INCLUDE_DIRECTORIES属性中都有正确的条目。
  • 如果您可以随意要求 CMake 2.8.11 作为最低要求,请考虑include_directories完全放弃并target_include_directories改用。这样做的优点是包括依赖项以专门的方式在每个目标的基础上得到解决,这通常是更理想的行为。

回答by summer.icecream

It maybe a scope problem. I feel what you are trying to do here is to propagate setting from the /project/external/foo/CMakeListsto /project/CMakeListsand such that this setting can be propagated to /project/src/CMakeLists. But unfortunately, propagation from lower-level to higher-level CMakeLists is not possible in cmake, except for cached values. This means you will also need to add include_directories(${CMAKE_SOURCE_DIR}/external/foo/include) in the /project/src/CMakeLists.txt. Or, as you already did, you can just add this line in the top-level CMakeLists.

这可能是范围问题。我觉得您在这里尝试做的是将设置从/project/external/foo/CMakeListsto /project/CMakeLists传播到/project/src/CMakeLists. 但不幸的是,除了缓存值之外,在 cmake 中不可能从较低级别的 CMakeLists 传播到较高级别的 CMakeLists。这意味着您还需要${CMAKE_SOURCE_DIR}/external/foo/include/project/src/CMakeLists.txt. 或者,正如您已经做的那样,您可以在顶级 CMakeLists.txt 中添加这一行。