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

CMake中目标关联的add_custom_command总是执行的问题求助

解决:仅在目标实际更新时执行自定义命令

简化场景的问题修复

你当前的核心问题是add_custom_target的依赖声明错误:

add_custom_target(T1 ALL DEPENDS t1.txt T1)

这里把目标T1自身作为依赖,形成了循环依赖,导致CMake每次构建都会判定T1需要重新生成,进而触发绑定的POST_BUILD命令。

另外,POST_BUILD类型的自定义命令绑定到自定义目标时,只要目标被触发(哪怕没有实际文件更新)就会执行。要实现仅当t1.txt更新时才执行追加操作,需要把追加逻辑转化为生成一个标记文件,让T1依赖这个标记文件,而非依赖目标自身或使用POST_BUILD。

修正后的代码:

cmake_minimum_required(VERSION 3.10)
project(proj12 NONE)

# 生成t1.txt的基础规则
add_custom_command(
    OUTPUT t1.txt
    COMMAND echo "Created at `date`" > t1.txt
    COMMENT "Creating file.."
)

# 追加内容并生成标记文件:仅当t1.txt变化时执行
add_custom_command(
    OUTPUT t1_appended.stamp
    COMMAND echo "Appended at `date`" >> t1.txt
    COMMAND touch t1_appended.stamp  # 标记操作完成,用于判断是否需要重新执行
    DEPENDS t1.txt
    COMMENT "Appending file.."
)

# 伪目标依赖标记文件,确保仅当依赖更新时触发操作
add_custom_target(T1 ALL DEPENDS t1_appended.stamp)

测试效果:

  • 首次make:执行创建和追加命令;
  • 再次make:无文件变化,不会执行任何命令。

实际Jar资源问题的适配方案

针对你提到的旧版UseJava模块add_jar资源命名空间错误的问题,同样可以用标记文件思路实现仅当Jar或资源变化时追加资源:

cmake_minimum_required(VERSION 3.10)
project(MyJavaProject)

find_package(Java REQUIRED)
include(UseJava)

# 仅编译Java文件生成基础Jar(不包含资源)
add_jar(MyJar SOURCES src/com/example/*.java)

# 收集所有资源文件
file(GLOB_RECURSE RESOURCES resources/**/*)

# 定义追加资源的命令,生成标记文件
add_custom_command(
    OUTPUT jar_resources_updated.stamp
    # 用jar命令追加资源到Jar包,注意调整资源的路径映射(按需修改)
    COMMAND jar uf $<TARGET_FILE:MyJar> -C resources/ .
    COMMAND touch jar_resources_updated.stamp
    DEPENDS MyJar ${RESOURCES}  # 依赖Jar包和资源文件,任一变化则执行
    COMMENT "Adding resources to Jar.."
)

# 创建目标确保资源追加操作执行,且仅在依赖变化时触发
add_custom_target(UpdateJarResources ALL DEPENDS jar_resources_updated.stamp)
add_dependencies(UpdateJarResources MyJar)

这个方案中,只有当MyJar因Java文件修改而更新,或者资源文件有变动时,才会执行jar uf命令添加资源,避免了每次构建重复执行的问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.30 03:45:34