【问题标题】:CMake, source_group used incorrectly or has incorrect behaviour?CMake、source_group 使用不正确或行为不正确?
【发布时间】:2013-06-26 05:19:09
【问题描述】:

在 CMake 中使用 source_group 来组织源文件(在本例中为 Xcode)结果比预期的更乏味。

set(REG1 ".*/some_folder1/")
set(REG2 ".*/some_folder2/")
set(REC ".*([.]cpp|[.]c)")

source_group("src" REGULAR_EXPRESSION "${REC}" )
source_group("src\\some_group" REGULAR_EXPRESSION "${REG1}${REC}" )
source_group("src\\some_other_group" REGULAR_EXPRESSION "${REG2}${REC}" )

我希望以上内容将 some_folder1 中的所有源文件放在 IDE 的 src/some_group 中,将 some_folder2 放在 src/some_other_group 中,其余文件直接放在 src 组中。

但是,结果是所有文件都直接进入了 src 组。

如果我删除第一个 source_group-line 并且只使用两个不重叠的:

source_group("src\\some_group" REGULAR_EXPRESSION "${REG1}${REC}" )
source_group("src\\some_other_group" REGULAR_EXPRESSION "${REG2}${REC}" )

行为几乎符合预期。 IE。所有匹配这两个正则表达式的文件都按预期组织,但其余文件进入 Xcode 创建的默认“源文件”组(不同的 IDE 将有不同的默认文件夹)。

所以看起来第一个 source_group 以某种方式覆盖了其余两个,即使 CMake 的文档说明相反(摘自 CMake 关于 source_group 的文档):

如果一个文件匹配多个组, 明确列出文件的 LAST 组将受到青睐,如果有的话。如果没有组 显式列出文件,其正则表达式与文件匹配的 LAST 组 会受到青睐。

这是由于我的一些误解还是 CMake->source_group 实际上的行为方式与宣传的不同?

我在 OSX 平台上使用 cmake 版本 2.8.10。

【问题讨论】:

  • 附言。我知道在我给出的特定示例中,映射是“文件夹-> 组”,可以在文件(GLOB ...)级别上进行组织,但真正的问题比这更普遍。

标签: c++ xcode build cmake


【解决方案1】:

是的,看起来源组生成不正确。如果您对解决方法感兴趣,可以重写第一个正则表达式以不匹配其他组:

cmake_minimum_required(VERSION 2.8.4)
project(example_simple CXX)

file(
    GLOB
    src
    "${CMAKE_CURRENT_SOURCE_DIR}/src/*.cpp"
    "${CMAKE_CURRENT_SOURCE_DIR}/src/*.c"
    "${CMAKE_CURRENT_SOURCE_DIR}/headers/*.hpp"
    "${CMAKE_CURRENT_SOURCE_DIR}/headers/*.h"
)

add_executable(simple_bin ${src})

set(REG_SRC ".*/src/")
set(REG_HDR ".*/headers/")
set(REG_EXT "[^/]*([.]cpp|[.]c|[.]h|[.]hpp)$")

source_group("src" REGULAR_EXPRESSION "${CMAKE_CURRENT_SOURCE_DIR}/${REG_EXT}")
source_group("src\\[sources]" REGULAR_EXPRESSION "${REG_SRC}${REG_EXT}")
source_group("src\\[headers]" REGULAR_EXPRESSION "${REG_HDR}${REG_EXT}")

或编写您自己的正则表达式命令并使用 FILES,而不是 REGULAR_EXPRESSION:

cmake_minimum_required(VERSION 2.8.4)
project(example_simple CXX)

file(
    GLOB
    src
    "${CMAKE_CURRENT_SOURCE_DIR}/src/*.cpp"
    "${CMAKE_CURRENT_SOURCE_DIR}/src/*.c"
    "${CMAKE_CURRENT_SOURCE_DIR}/headers/*.hpp"
    "${CMAKE_CURRENT_SOURCE_DIR}/headers/*.h"
)

add_executable(simple_bin ${src})

set(REG_SRC ".*/src/")
set(REG_HDR ".*/headers/")
set(REG_EXT ".*([.]cpp|[.]c|[.]h|[.]hpp)")

foreach(filename ${src})
  string(REGEX MATCH "${REG_SRC}${REG_EXT}" match_group_sources ${filename})
  string(REGEX MATCH "${REG_HRD}${REG_EXT}" match_group_headers ${filename})
  if(match_group_sources)
    list(APPEND group_sources ${filename})
  elseif(match_group_headers)
    list(APPEND group_headers ${filename})
  else()
    list(APPEND group_other ${filename})
  endif()
endforeach()

source_group("src" FILES ${group_other})
source_group("src\\[sources]" FILES ${group_sources})
source_group("src\\[headers]" FILES ${group_headers})

【讨论】:

  • 好吧,我的整个 CMake 不适合在此处发布(也已对其进行了一些修改以通过更细粒度的文件(GLOB 表达式)来解决上述问题。但是处理源文件的部分大致如上,除了我用GLOB列出源文件:file (GLOB src "${CMAKE_CURRENT_SOURCE_DIR}/src/*.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/src/*.c" "${CMAKE_CURRENT_SOURCE_DIR}/headers/*.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/headers/*.h")然后add_executable(${S_APP_name} ${src})
  • 感谢您的努力!这与我自己制作的解决方法相距不远(除了我在文件(GLOB 级别)上制作的。我仍然很好奇为什么 source_group 的行为与其文档不同,但我会将其归因于错误,直到另行通知并与 cmake 社区一起讨论 :)。
猜你喜欢
  • 2019-05-26
  • 2012-12-21
  • 2021-04-25
  • 2014-06-28
  • 2013-08-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多