用于在头文件更改时构建简单 c 项目重新编译的示例 makefile

Posted

技术标签:

【中文标题】用于在头文件更改时构建简单 c 项目重新编译的示例 makefile【英文标题】:Example makefile for building simple c project recompiling when headers change 【发布时间】:2014-02-19 04:57:36 【问题描述】:

有没有人有一个完整的makefile可以做以下事情:

    如果 HEADER 文件更改,则重建项目 cpp 文件在 makefile 中列出 头文件未在 makefile 中列出 头文件的名称可以与 cpp 文件不同 部分cpp文件没有头文件

我已经看到了关于如何让 make 工具找出头文件依赖项的说明,但是这些说明都没有提供任何类似于工作示例的东西。一个简单的例子如下: main.cpp C1.cpp C1.h C2.cpp C2.h

【问题讨论】:

【参考方案1】:
CXX = g++

OBJECTS := main.o C1.o C2.o

all: $(OBJECTS)

%.o : %.cpp
    $(CXX) $(CPPFLAGS) -Wall -MMD -c $< -o $@

-include *.d

编辑: 正如 TobySpeight 指出的那样,如果您构建目标文件、重命名或删除必备源文件或头文件之一,然后尝试重建目标文件,这将不起作用; .d 文件仍然需要丢失的文件,并且构建将失败。我忽略了包含处理这种情况的行:

%.h: ;
%.cpp: ;

(这很有效,但很粗略。更精确的做法是在%.o规则中放入一些sed命令,以便在.d文件中添加特定的空规则,每个先决条件一个,但sed命令很难看,上面的方法几乎适用于所有情况。)

【讨论】:

我认为你写错了:你的规则应该是%.d: %.cpp吗?我也会警惕包含*.d 而不是$(SOURCES:.cpp=.d) 或其他任何内容,因为当您重命名/删除源时,前者很容易中断。 @TobySpeight:我可以告诉你没有测试它。 是的,我当然测试过了。这就是我知道,当您删除和/或重命名标头时,您会遇到仍然引用已删除标头的依赖文件,而如果您显式生成依赖项,它们会在 makefile 被视为完全读取之前重新生成。您至少应该在您的clean 目标中包含$(RM) *.d,以便进行某种最后的恢复。 @TobySpeight:我道歉。我遗漏了解决方案的一个重要部分,然后忽略了正确测试它并指责你犯了这个错误。我将编辑我的答案并给出适当的答复... 使用-MMD -MP 是否解决了重命名或删除标题的问题,没有任何粗略或sed?它似乎对我有用,但我不知道是否有一些我没有得到的细微差别。 “此选项指示 CPP 为除主文件之外的每个依赖项添加虚假目标,从而导致每个依赖项都不依赖任何内容。如果您删除头文件而不更新 Makefile 以匹配,这些虚拟规则可以解决错误。”【参考方案2】:

您也可以为此使用 CMake。您需要编写的所有内容是:

add_executable (exec main.cpp C1.cpp C2.cpp)

【讨论】:

cmake 不是make,并且cmake 文件不是makefile

以上是关于用于在头文件更改时构建简单 c 项目重新编译的示例 makefile的主要内容,如果未能解决你的问题,请参考以下文章

是否有任何软件可以在文件更改时重新编译基于 CMake 的软件项目?

剃刀视图没有给出编译时错误[重复]

Flask 服务于 Vue.js 包文件。更改时重新编译?

Ufft示例编译

仅在项目发生更改时添加编译时间戳 (C)

这是弱引用的正确用法吗?