假设我有这个通用模式规则
%.txt:
touch $@
然后我可以毫无问题地调用以下命令
make foo.txt
make foo/bar.txt
make foo/bar/baz.txt
但是,假设我想要根据我正在构建的目标父目录的名称来指定特定逻辑
doc/%.txt:
echo "bla bla" >$@
data/%.txt
echo "bla bla bla" >$@
我可以调用
make doc/foo.txt
make data/foo.txt
但是以下会失败
make foo/bar/doc/baz.txt
make foo/bar/data/baz.txt
我知道这是如何模式匹配的结果,但我想知道是否有一种解决方法可以使Make考虑“带斜杠”的模式规则,就像任何其他“不带斜杠”的通用模式规则一样.
当然,任何基于模板的解决方案仅包含“复制”所有许多可能的子目录“路径”的规则是不可接受的。另外,我不能考虑“特殊”文件名,例如上面的示例,
%.doc.txt
和%.data.txt
,开关必须保持基于“目录”。
我想知道是否有一种解决方法可以使 Make 考虑“带斜杠”的模式规则,就像任何其他“不带斜杠”的通用模式规则一样。
不,没有。
但是还有其他选择。特别是,尽管您不希望每个目录都有单独的“显式”规则,但您可以考虑根据甚至可以动态生成的目录列表,从 makefile 本身中定义的一次规则模板生成此类规则。例如,也许这些内容会适合您:
doc_dirs := $(shell find . -type d -name doc)
data_dirs := $(shell find . -type d -name data)
define docfile_rule =
$(1)/%.txt:
echo "bla bla" >$$@
endef
define datafile_rule =
$(1)/%.txt:
echo "bla bla bla" >$$@
endef
$(foreach dir,$(dirs),$(eval $(call docfile_rule,$(dir))))
$(foreach dir,$(dirs),$(eval $(call datafile_rule,$(dir))))
我不认为这就是您反对模板时的意思。它允许您为每个感兴趣的目录中的目标定义不同风格的单独模式规则。不同规则风格的模板甚至看起来很像普通规则,这应该使它们相对易于维护。有有
一些警告,例如必须处理额外的扩展,但我认为这是相当可行的。