c++ - 需要帮助理解 makefile 模式规则 % : %. o

标签 c++ makefile

我想使用我在书中读到的模式规则将此 makefile 更改为更简单的内容:

VPATH = src
CPPFLAGS = -I include

main.o: main.cpp
    g++ $(CPPFLAGS) $<
TwoDimensionalShape.o: TwoDimensionalShape.cpp
    g++ -c $(CPPFLAGS) $<
Square.o: Square.cpp Square.h
    g++ -c $(CPPFLAGS) $<
Circle.o: Circle.cpp Circle.h
    g++ -c $(CPPFLAGS) $<
Rectangle.o: Rectangle.cpp Rectangle.h
    g++ -c $(CPPFLAGS) $<
Triangle.o: Triangle.cpp Triangle.h
    g++ -c $(CPPFLAGS) $<
ShapeStack.o: ShapeStack.cpp ShapeStack.h
    g++ -c $(CPPFLAGS) $<
ScreenManager.o: ScreenManager.cpp ScreenManager.h
    g++ -c $(CPPFLAGS) $<
ScreenState.o: ScreenState.cpp ScreenState.h
    g++ -c $(CPPFLAGS) $<
SquareState.o: SquareState.cpp SquareState.h
    g++ -c $(CPPFLAGS) $<
CircleState.o: CircleState.cpp CircleState.h
    g++ -c $(CPPFLAGS) $<

读完这本书后,我可以使用这样的模式规则来编写上面的内容。但我不明白它是如何工作的:

#source files are in "src" folder.
VPATH = src
#header files are in "include" folder.
CPPFLAGS = -I include -Wall

all: main.o TwoDimensionalShape.o Square.o Circle.o Rectangle.o Triangle.o ShapeStack.o ScreenManager.o ScreenState.o SquareState.o CircleState.o
    g++ $(CPPFLAGS) $^

%.o: %.cpp
    g++ -c $(CPPFLAGS) $<

%: %.o
    g++ $<

这个生成文件是正确的,但我不明白它是如何工作的。

  1. 如果我更改了例如 2 个源文件,这个 makefile 如何理解只编译更改的两个源文件而不是所有源文件?
  2. 在我读的书中,示例是关于 C 而不是 C++,最后一行是 %: %.c。那为什么我的行是 %: %.o 工作?不应该是 %: %.cpp 吗?

最佳答案

This makefile is correct however I don't understand how it is working.

如果您的新 Makefile 是旧 Makefile 的替代品,那么它肯定无法正常工作。

在“旧”的你有例如

ShapeStack.o: ShapeStack.cpp ShapeStack.h

这表明 ShapeStack.o 依赖于 .cpp 和头文件。您的新 Makefile 与其他文件没有任何依赖关系,这会导致很多麻烦。只需触摸您的标题之一并输入 make。什么都不会发生!

所以至少你必须引入你的源文件依赖关系,可能像在你的旧 makefile 中那样手动,或者使用编译器的依赖性检查的更多自动化,使用 gcc 它是“gcc -MM”。

要获得自动化先决条件,请参阅 https://www.gnu.org/software/make/manual/html_node/Automatic-Prerequisites.html

并且使用 vpath 会导致很多麻烦。有一些文章,例如: http://make.mad-scientist.net/papers/how-not-to-use-vpath/

一些示例 Makefile 可以在这里找到: minimum c++ make file for linux

关于c++ - 需要帮助理解 makefile 模式规则 % : %. o,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50018305/

相关文章:

c++ - CUDA 代码在 Linux 上编译但在 Windows 上不编译(Visual Studio 2012)

c++ - 将 C++ 项目导入到 Eclipse - 重叠工作区

c++ - makefile 中的 qt gui 项目错误

c++ - 如何添加现有的lib需要构建到我自己的项目中

mysql - C 和 Mysql 中的链接错误

c++ - 共享内存中进程间的屏障实现

c++ - 从 'DWORD (*)(void*)' 到 'DWORD (*)(void*)' 的无效转换

c++ - 使用 make 自动生成 Moc Qt 头文件

c++ - 多个库和 boost 序列化

c++ - Qt - QList 常量正确性