You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用CMake复制可执行文件及依赖时排除自动生成的CMake文件?

CMake复制文件时排除冗余内容并添加外部依赖的解决办法

问题背景

用CMake构建共享库my_library和可执行文件executable,要求二者最终放在同一特定目录下。需要复制可执行文件及其依赖(包括非目标关联的外部共享库)到该目录,但要排除CMake生成的cmake_install.cmake和CMakeFiles/这类冗余文件/目录。当前配置用copy_directory会把整个输出目录都复制过来,包含了不需要的内容,需要调整实现方式。

可行解决方案

1. 用CMake 3.21+的copy_directory排除功能

从CMake 3.21开始,copy_directory支持--exclude参数,直接指定要排除的内容,修改executable/CMakeLists.txt里的自定义命令:

add_custom_command(
        TARGET executable 
        POST_BUILD
        COMMAND ${CMAKE_COMMAND} -E copy_directory
        --exclude "cmake_install.cmake"
        --exclude "CMakeFiles/"
        $<TARGET_FILE_DIR:executable>
        $<TARGET_FILE_DIR:my_library>/bin/${PLATFORM_NAME}${PROCESSOR_ARCH}
)

这样复制时会自动跳过指定的文件和目录,简单直接。

2. 手动复制所需文件(兼容旧版CMake)

如果用的是3.21之前的CMake版本,没法用--exclude,就精准复制需要的文件类型,避免带进来冗余内容:

add_custom_command(
        TARGET executable 
        POST_BUILD
        # 复制可执行文件本身
        COMMAND ${CMAKE_COMMAND} -E copy
        $<TARGET_FILE:executable>
        $<TARGET_FILE_DIR:my_library>/bin/${PLATFORM_NAME}${PROCESSOR_ARCH}/$<TARGET_FILE_NAME:executable>
        # 复制可执行文件的依赖库(自动适配平台:Windows是dll,Linux是so,macOS是dylib)
        COMMAND ${CMAKE_COMMAND} -E copy_if_different
        $<TARGET_RUNTIME_DLLS:executable>
        $<TARGET_FILE_DIR:my_library>/bin/${PLATFORM_NAME}${PROCESSOR_ARCH}/
)

这种方式只复制必要的文件,完全不会包含CMake生成的冗余内容。

3. 复制非目标关联的外部共享库

对于不属于executable目标依赖的外部库,单独添加复制命令即可,比如:

# 假设外部库路径是EXTERNAL_LIB_PATH,文件名根据平台调整(如external_lib.dll/libexternal_lib.so/libexternal_lib.dylib)
add_custom_command(
        TARGET executable 
        POST_BUILD
        COMMAND ${CMAKE_COMMAND} -E copy_if_different
        ${EXTERNAL_LIB_PATH}/external_lib.dll
        $<TARGET_FILE_DIR:my_library>/bin/${PLATFORM_NAME}${PROCESSOR_ARCH}/
)

多个外部库的话,重复添加COMMAND行或者用循环处理都可以。

4. 优化:直接设置统一输出目录(更省心)

其实可以一开始就把共享库和可执行文件的输出目录设为目标目录,避免后续复制操作:
在根目录的CMakeLists.txt里添加:

# 设置统一的输出目录,直接生成到目标路径
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin/${PLATFORM_NAME}${PROCESSOR_ARCH})
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin/${PLATFORM_NAME}${PROCESSOR_ARCH})

这样my_library和executable会直接生成到指定目录,不需要额外复制,之后只需要处理外部共享库的复制就行。

内容的提问来源于stack exchange,提问作者dan123123

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.23 04:27:14