我想删除makefile中的配方重复,如下所示
SHELL := /bin/bash
a_% : a1_% a2_%
cat $^ > $@
b_% : b1_% b2_% %_b3
cat $^ > $@
但以下情况不起作用。我想this SO question中的技巧不适用于模式规则。
SHELL := /bin/bash
a_% : a1_% a2_%
b_% : b1_% b2_% %_b3
a_% b_%:
cat $^ > $@
有什么建议吗? (在我原来的makefile中,配方重复发生在4个目标中,每个目标都有3个替换,所以我无法展开目标)
- EDIT-- 我意识到解决这个问题的一种方法是:
CMD1 = cat $^ > $@
a_% : a1_% a2_%
$(CMD1)
b_% : b1_% b2_% %_b3
$(CMD1)
答案 0 :(得分:1)
我相信这符合你的要求:
SHELL := /bin/bash
define STUFF
$(1)_%: $(1)1_% $(1)2_% $(2)
cat $$^ > $$@
endef
$(eval $(call STUFF,a))
$(eval $(call STUFF,b,%_b3))
这是如何运作的:
规则的一般形式定义为STUFF
。 (您显然希望在自己的Makefile中使用更好的名称。)请注意$$^
和$$@
中的美元符号加倍。这可以在执行$(call ...)
时保护他们免受评估。 $(1)
和$(2)
将被$(call ...)
替换为位置参数。
$(call STUFF,a)
“调用”STUFF
,$(1)
设置为字符串a
,$(2)
设置为空字符串。返回值为:
a_%: a1_% a2_%
cat $^ > $@
注意如何从剩余的变量中删除一个$
。
$(eval ...)计算在上一步中获得的返回值,就好像该字符串已放入Makefile中一样。所以它创造了规则。
b
文件也会发生第2步和第3步。它类似于a
文件的情况,但此时$(2)
设置为字符串%_b3
。
这基本上是我过去使用的方法,以避免在规则相当复杂的情况下重复规则。对于您在问题中显示的特定案例,我将使用您在问题中提到的共享命令变量。