如何将多个目标与其先决条件进行模式匹配?
How to pattern-match multiple targets with their prerequisities?
我刚开始使用 makefile,我对模式的工作原理有点困惑。我有多个不同的目标,每个目标都有一个名称匹配的先决条件。我希望有一个变量在顶部存储目标和先决条件的所有“词干”,然后只需添加 prefix/suffix 和所有这些的通用配方。到目前为止我已经尝试过:
names = stem1 stem2 stem3
all: $(names:%=dir/prefix_%.txt) $(names:%=dir/another_%.txt)
$(names:%=dir/prefix_%.txt): $(names:%=sourcedir/yetanother_%.xlsx)
echo $@
echo prerequisite_with_the_same_stem_as_current_target
尽管这使得所有目标都一一列出,但每个目标的先决条件都列出了,而不仅仅是与目标的当前 %(names)
匹配的条件。我需要它匹配的原因是因为我随后将当前目标及其唯一先决条件提供给脚本,然后脚本生成目标。如何将每个先决条件与其一个目标进行模式匹配?
您对 make
如何处理列表有误解。如果你有一个变量:
names = stem1 stem2 stem3
然后 make
将其作为列表处理 但每次您命名此变量时都会立即实例化整个列表内容 。 它不会对列表内容进行一对一的操作,因为那将接近于不可控,视情况而定。相反,它求助于简单的文本替换,因此你的行
all: $(names:%=dir/prefix_%.txt) $(names:%=dir/another_%.txt)
被解析&变量替换成一个字符串非常简单:
all: dir/prefix_stem1.txt dir/prefix_stem2.txt dir/prefix_stem3.txt ...etc...
迭代列表处理仅在 $(names:%=dir/prefix_%.txt)
内发生,依此类推,而行本身在变量替换后只是被提供给第二个解析步骤的文本。
符合你的规则:
$(names:%=dir/prefix_%.txt): $(names:%=sourcedir/yetanother_%.xlsx)
扩展到
dir/prefix_stem1.txt dir/prefix_stem2.txt dir/prefix_stem3.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
这是三个规则的简写符号:
dir/prefix_stem1.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
dir/prefix_stem2.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
dir/prefix_stem3.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
仅此而已。显然,您告诉 make 每个目标都取决于 所有 的先决条件。
稍加调整 Static Pattern Rules 您就可以实现目标,不过:
MY_TARGETS := $(names:%=dir/prefix_%.txt) # create full target names
$(MY_TARGETS) : dir/prefix_%.txt : sourcedir/yetanother_%.xslx
我刚开始使用 makefile,我对模式的工作原理有点困惑。我有多个不同的目标,每个目标都有一个名称匹配的先决条件。我希望有一个变量在顶部存储目标和先决条件的所有“词干”,然后只需添加 prefix/suffix 和所有这些的通用配方。到目前为止我已经尝试过:
names = stem1 stem2 stem3
all: $(names:%=dir/prefix_%.txt) $(names:%=dir/another_%.txt)
$(names:%=dir/prefix_%.txt): $(names:%=sourcedir/yetanother_%.xlsx)
echo $@
echo prerequisite_with_the_same_stem_as_current_target
尽管这使得所有目标都一一列出,但每个目标的先决条件都列出了,而不仅仅是与目标的当前 %(names)
匹配的条件。我需要它匹配的原因是因为我随后将当前目标及其唯一先决条件提供给脚本,然后脚本生成目标。如何将每个先决条件与其一个目标进行模式匹配?
您对 make
如何处理列表有误解。如果你有一个变量:
names = stem1 stem2 stem3
然后 make
将其作为列表处理 但每次您命名此变量时都会立即实例化整个列表内容 。 它不会对列表内容进行一对一的操作,因为那将接近于不可控,视情况而定。相反,它求助于简单的文本替换,因此你的行
all: $(names:%=dir/prefix_%.txt) $(names:%=dir/another_%.txt)
被解析&变量替换成一个字符串非常简单:
all: dir/prefix_stem1.txt dir/prefix_stem2.txt dir/prefix_stem3.txt ...etc...
迭代列表处理仅在 $(names:%=dir/prefix_%.txt)
内发生,依此类推,而行本身在变量替换后只是被提供给第二个解析步骤的文本。
符合你的规则:
$(names:%=dir/prefix_%.txt): $(names:%=sourcedir/yetanother_%.xlsx)
扩展到
dir/prefix_stem1.txt dir/prefix_stem2.txt dir/prefix_stem3.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
这是三个规则的简写符号:
dir/prefix_stem1.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
dir/prefix_stem2.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
dir/prefix_stem3.txt: sourcedir/yetanother_stem1.xlsx sourcedir/yetanother_stem2.xlsx sourcedir/yetanother_stem3.xlsx
仅此而已。显然,您告诉 make 每个目标都取决于 所有 的先决条件。
稍加调整 Static Pattern Rules 您就可以实现目标,不过:
MY_TARGETS := $(names:%=dir/prefix_%.txt) # create full target names
$(MY_TARGETS) : dir/prefix_%.txt : sourcedir/yetanother_%.xslx