问题描述
#!make
.PRECIoUS: a/b/c/%_pqr
a/b/c/%_pqr:
echo $@
touch $@
.PRECIoUS: a/b/c/%_abc
a/b/c/%_abc: a/b/c/pqr_pqr
echo $@
touch $@
当我第一次运行时,它尊重它的依赖性:
make a/b/c/pqr_abc -f 1.mk
echo a/b/c/pqr_pqr
a/b/c/pqr_pqr
touch a/b/c/pqr_pqr
echo a/b/c/pqr_abc
a/b/c/pqr_abc
touch a/b/c/pqr_abc
但是,如果我删除“ a / b / c / pqr_pqr”文件,然后再次运行此目标,则它并不需要做:
rm -f a/b/c/pqr_pqr; make a/b/c/pqr_abc -f 1.mk
make: `a/b/c/pqr_abc' is up to date.
根据我的理解,它应该再次运行两个目标。 请有人帮我。
解决方法
两个目标都是隐式的,因此是中间的。根据{{3}}:
第一个区别是如果中间文件不存在会发生什么。 [...]但是,如果b是中间文件,则make可以单独放置。除非更新b的某些先决条件或有其他原因更新该目标,否则不会麻烦更新b或最终目标。
因此,由于 pqr_abc 已经存在,并且 pqr_pqr 是中间文件,没有任何先决条件(因此,先决条件没有变化),因此将不会重新生成它。
根据制造商的理解,只需创建 pqr_pqr 即可从中生成 pqr_abc (这是中间文件的定义),并且由于 pqr_abc 已经存在,无需重新生成它。
如果您希望每次都重新生成该文件,则必须明确提及该文件,以便不再将其视为中间文件,即:
$ cat Makefile
a/b/c/%_pqr:
touch $@
a/b/c/%_abc: a/b/c/pqr_pqr
touch $@
a/b/c/pqr_pqr:
最后一行定义了显式目标,但没有定义配方,该配方仍将从隐式规则中调用。请注意,它将不再被认为是中间的,也不会被自动删除,因此也不需要.PRECIOUS
指令。
输出:
$ make a/b/c/pqr_abc
touch a/b/c/pqr_pqr
touch a/b/c/pqr_abc
$ make a/b/c/pqr_abc
make: 'a/b/c/pqr_abc' is up to date.
$ rm a/b/c/pqr_pqr
$ make a/b/c/pqr_abc
touch a/b/c/pqr_pqr
touch a/b/c/pqr_abc