为什么这个makefile会删除我的目标?

Łuk*_*Lew 21 makefile

一个最小的例子:

%.txt: foo.log
    # pass

%.log:
    # pass
Run Code Online (Sandbox Code Playgroud)

跑:

$ make a.txt --dry-run
# pass
# pass
rm foo.log
Run Code Online (Sandbox Code Playgroud)

为什么最后一个动作是rm foo.log?如何摆脱它?

Sea*_*ean 26

默认情况下,GNU make会删除中间文件.由于%.txt依赖于%.log,因此想要删除.log文件.为了防止这种行为,您可以使用.PRECIOUS或.SECONDARY将它们标记为珍贵.

.PRECIOUS: foo.log
Run Code Online (Sandbox Code Playgroud)

此外,您可以通过使用没有依赖项的.SECONDARY来删除任何中间文件.

.SECONDARY:
Run Code Online (Sandbox Code Playgroud)

请参阅GNU make手册的这一部分.


Bet*_*eta 6

您正在a.txt通过一系列隐式规则(在本例中为您自己定义的隐式规则)进行制作.因此,Make会考虑foo.log一个中间文件,并在达到其目的时将其删除.您可以通过声明foo.logSECONDARY目标来覆盖此行为:

.SECONDARY: foo.log
Run Code Online (Sandbox Code Playgroud)

  • 如果您希望保留所有中间体,只需声明.SECONDARY的目标:没有依赖关系.或者,您可以将通配符与.PRECIOUS一起使用.即.PRECIOUS:%.log (5认同)
  • 我知道,但这就是手册所说的.如果您曾阅读过该手册,那么您就知道这并不是最令人惊讶的不一致. (4认同)
  • .SECONDARY:%.log#不起作用,我该怎么做才能使规则一般? (2认同)
  • @Sean:奇怪的是,通配符适用于PRECIOUS,但不适用于SECONDARY ...... (2认同)