【发布时间】:2019-07-12 11:36:08
【问题描述】:
我有一个具有这种玩具结构的项目:
src:
obj1.cpp
obj2.cpp
obj:
(empty folder)
我想使用make 编译成一个库。我想在我的 makefile 中写的是:
mylib.a: obj1.o obj2.o
ar $@ $^
这可行,但是它使文件夹变得混乱,因为它导致了这种结构:
obj1.o
obj2.o
mylib.a
src:
obj1.cpp
obj2.cpp
obj:
(empty folder)
我希望调用的结果是这样的:
mylib.a
src:
obj1.cpp
obj2.cpp
obj:
obj1.o
obj2.o
其中两个obj 源都被编译成obj 中的.o 对象。我尝试在我的 makefile 中这样做:
vpath %.o obj
mylib.a: obj1.o obj2.o
但这与上面的结果相同。所以,我很确定,obj1.o 的隐式规则不知道输出到哪里,对吧?好的,所以我添加了这条规则:
%.o: %.cpp
g++ $^ -o obj/$@
为了确保我正在编译成obj,但是,现在 make 命令失败了,我明白为什么它失败了。它失败是因为 mylib 找到了 obj1.o,因为它找到了它的规则,它执行了规则,但是规则并没有导致 obj1.o 的存在,而是导致 obj/obj1.o 的存在,所以当mylib 是组合的,它的规则是 ar obj1.o obj2.o 并且它失败了。
所以,我的问题是:有没有一种简单而优雅的方法来避免这个问题?
我看到的一个解决方案是始终有一些文件,如果需要,则为空,在obj 中命名为 obj1.o,但这对我来说似乎很难看。另一个是添加
"obj/" 到 mylib.a 的每个对象,但这意味着重复代码,甚至更丑陋。那么,解决这个问题的最佳方法是什么?
【问题讨论】:
-
在应该在该目录中的每个路径前指定
obj/是标准解决方案,如果使用模式规则,则不会特别冗长或混乱。