多个目标的Makefile优化
Makefile optimisation of multiple targets
因此,作为我用 C++ 制作的一些工具的一部分,我希望能够单独测试每个工具。有多个工具和多个测试文件,因此我想要多个可执行文件作为我的最终结果。我希望 Makefile 的魔力能让我的生活更轻松。
这是我当前的 Makefile 模板:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: lbLog lbString
lbLog:
$(CXX) $(CXXFLAGS) 'src/lbLog.cpp' -o lbLog.o
$(CXX) 'examples/lbLog_example.cpp' lbLog.o -o 'tests/lbLog_example'
rm lbLog.o
lbString:
$(CXX) $(CXXFLAGS) 'src/lbString.cpp' -o lbString.o
$(CXX) 'examples/lbString_example.cpp' lbString.o -o 'tests/lbString_example'
rm lbString.o
预期的文件结构是
- driver 示例文件位于“/examples”(.cpp)
- sources/tools (.cpp) 在 '/src'
- headers 在“/include”
- 在“/tests”中输出 exe
所以问题是,有没有办法优化makefile,这样我就可以虚拟'set and forget'?我不想满怀希望地将每个新工具都添加到 Makefile 中。因为这是一个重复的模式,所以必须有办法让它变得聪明。
假设您可以确定从源代码生成工具的规则,请查看这些 make 函数:
- patsubst
- 通配符
这根本不是一个合适的 makefile。它没有指定 make 可以利用的任何 prerequisite/target 对。
要利用 make 为您做的事情,您需要更像这样的东西:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: tests/lbLog_example tests/lbString_example
lbLog.o: src/lbLog.cpp
$(CXX) $(CXXFLAGS) $^ -o $@
tests/lbLog_example: examples/lbLog_example.cpp lbLog.o
$(CXX) $^ -o $@
lbString.o: src/lbString.cpp
$(CXX) $(CXXFLAGS) $^ -o $@
tests/lbString_example: examples/lbString_example.cpp lbString.o
$(CXX) $^ -o $@
这告诉 make 默认构建测试可执行文件,并且测试可执行文件依赖于顶层目标文件以及如何从各自的源构建目标文件。现在 make 知道它需要在目标文件的先决条件文件发生变化时重建目标文件,而不是其他情况(与总是重新编译所有内容的原始文件相反)。
您甚至可以像这样使用 pattern rules 进一步清理它:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: tests/lbLog_example tests/lbString_example
lb%.o: src/lb%.cpp
$(CXX) $(CXXFLAGS) $^ -o $@
tests/lb%_example: examples/lb%_example.cpp lb%.o
$(CXX) $^ -o $@
如果您允许在 src
目录中构建目标文件,您也可以完全删除 lb%.o: src/lb%.cpp
规则。在 examples
目录中构建测试可执行文件,我相信您也可以从 tests/lb%_example: examples/lb%_example.cpp lb%.o
目标中删除 $(CXX) $^ -o $@
主体,我相信这将以这个(未经测试的)makefile 结束:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: tests/lbLog_example tests/lbString_example
tests/lb%_example: examples/lb%_example.cpp lb%.o
这最后一点有效(假设我没问题)因为 make 带有许多 built-in rules 常见的构建模式。
因此,作为我用 C++ 制作的一些工具的一部分,我希望能够单独测试每个工具。有多个工具和多个测试文件,因此我想要多个可执行文件作为我的最终结果。我希望 Makefile 的魔力能让我的生活更轻松。
这是我当前的 Makefile 模板:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: lbLog lbString
lbLog:
$(CXX) $(CXXFLAGS) 'src/lbLog.cpp' -o lbLog.o
$(CXX) 'examples/lbLog_example.cpp' lbLog.o -o 'tests/lbLog_example'
rm lbLog.o
lbString:
$(CXX) $(CXXFLAGS) 'src/lbString.cpp' -o lbString.o
$(CXX) 'examples/lbString_example.cpp' lbString.o -o 'tests/lbString_example'
rm lbString.o
预期的文件结构是
- driver 示例文件位于“/examples”(.cpp)
- sources/tools (.cpp) 在 '/src'
- headers 在“/include”
- 在“/tests”中输出 exe
所以问题是,有没有办法优化makefile,这样我就可以虚拟'set and forget'?我不想满怀希望地将每个新工具都添加到 Makefile 中。因为这是一个重复的模式,所以必须有办法让它变得聪明。
假设您可以确定从源代码生成工具的规则,请查看这些 make 函数:
- patsubst
- 通配符
这根本不是一个合适的 makefile。它没有指定 make 可以利用的任何 prerequisite/target 对。
要利用 make 为您做的事情,您需要更像这样的东西:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: tests/lbLog_example tests/lbString_example
lbLog.o: src/lbLog.cpp
$(CXX) $(CXXFLAGS) $^ -o $@
tests/lbLog_example: examples/lbLog_example.cpp lbLog.o
$(CXX) $^ -o $@
lbString.o: src/lbString.cpp
$(CXX) $(CXXFLAGS) $^ -o $@
tests/lbString_example: examples/lbString_example.cpp lbString.o
$(CXX) $^ -o $@
这告诉 make 默认构建测试可执行文件,并且测试可执行文件依赖于顶层目标文件以及如何从各自的源构建目标文件。现在 make 知道它需要在目标文件的先决条件文件发生变化时重建目标文件,而不是其他情况(与总是重新编译所有内容的原始文件相反)。
您甚至可以像这样使用 pattern rules 进一步清理它:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: tests/lbLog_example tests/lbString_example
lb%.o: src/lb%.cpp
$(CXX) $(CXXFLAGS) $^ -o $@
tests/lb%_example: examples/lb%_example.cpp lb%.o
$(CXX) $^ -o $@
如果您允许在 src
目录中构建目标文件,您也可以完全删除 lb%.o: src/lb%.cpp
规则。在 examples
目录中构建测试可执行文件,我相信您也可以从 tests/lb%_example: examples/lb%_example.cpp lb%.o
目标中删除 $(CXX) $^ -o $@
主体,我相信这将以这个(未经测试的)makefile 结束:
# Compilation
CXX = g++
CXXFLAGS = -pedantic -Wall -c # -g -Wextra
all: tests/lbLog_example tests/lbString_example
tests/lb%_example: examples/lb%_example.cpp lb%.o
这最后一点有效(假设我没问题)因为 make 带有许多 built-in rules 常见的构建模式。