Makefile 我试图定义一个字符串X=";要么';这|那'&引用;但GNU make won';我不能接受

Makefile 我试图定义一个字符串X=";要么';这|那'&引用;但GNU make won';我不能接受,makefile,gnu-make,Makefile,Gnu Make,我正在尝试为gnumake编写一个Makefile。我不知道这里有什么问题: foo := this|works bar := "I lost my 'single quotes'" baz := 'make|will|not|accept|this|with|the|single|quotes' whatIWant := "A string with its 'single|quoted|regex|alternatives'" this-almost-works: #But the s

我正在尝试为gnumake编写一个Makefile。我不知道这里有什么问题:

foo := this|works
bar := "I lost my 'single quotes'"
baz := 'make|will|not|accept|this|with|the|single|quotes'

whatIWant := "A string with its 'single|quoted|regex|alternatives'"

this-almost-works:  #But the single quotes are lost.
        @printf '%s ' "$(whatIWant)"

this-fails-horribly:
        @printf '$(whatIWant)'
我收到以下错误消息

/bin/sh: 1: quoted: not found
/bin/sh: 1: /bin/sh: 1: regex: not foundalternatives": not found

blah blah Error 127
  • 为什么它要在shell中运行这个字符串的一部分

  • 如何定义一个变量来精确地包含whatIWant的内容


  • 可能值得详细查看扩展

    在定义变量时, 几乎唯一有效果的字符是
    $
    。 其他一切都是照字面理解的。 忽略赋值运算符(
    =
    :=
    )周围的空白是毫无意义的

    foo  :=     this|works
    
    foo
    被分配了文本
    this |起作用
    。 同样地

    baz := 'make|will|not|accept|this|with|the|single|quotes'
    
    将文本
    “make | will | not | accept | this |与| single | quotes'
    分配给
    baz
    。 漂亮漂亮

    现在,当make决定构建
    时,它会失败得很惨
    (可能是因为您对shell说,
    使其失败得可怕
    ) 它会在执行任何操作之前展开命令块。 不无道理,,
    $(whatIWant)
    替换为
    “一个字符串,其'single | quoted | regex | alternatives'”
    。 再一次,很好,很漂亮。 剩下的就是逐字传递给shell,一次一行。 贝壳看见了

    printf '"A string with its 'single|quoted|regex|alternatives'"'
    
    (如果您不使用
    @
    前缀,该品牌会对您产生帮助)。 现在我们在壳牌的报价领域

    • printf
      命令被传递一个参数:
      “一个字符串及其单个
      • 带有“的字符串是单引号字符串。shell去掉了
        s,留下了文本
        ,一个带有
        的字符串
      • single
        中没有元字符,因此shell将其单独保留
    • 输出通过管道传输到
      quoted
      命令
    • 输出通过管道传输到
      regex
      命令
    • 输出通过管道传输到
      alternatives”
      命令
      • shell将看到单引号字符串
        '='
        ,去掉引号,留下一个文本
        =
        ,并将其附加到单词
        替代项中
    没有语法错误。 当shell尝试设置管道时,它会查找
    替代项“
    命令。 它在它的
    $PATH
    目录中找不到一个,因此它会以消息
    /bin/sh:1:/bin/sh:1:regex:not foundAlternations:not found
    停止

    一种可能的编码:

    .PHONY: this-workes-nicely
    this-workes-nicely:
        echo $(whatIWant)
    

    尽管您可能会发现,首先将引号保留在变量定义之外更为简洁。

    如果我没记错的话,请用“\”转义管道。管道是makefilesCool中的特殊字符。这有助于避免错误消息。虽然我真的不明白为什么foo有效而baz无效。我仍然需要保留那些单引号。出于某种原因,它们消失了。Make不解释引号,它们在字符串中。因此,您在这里真正要做的是:
    @printf“%s”一个带“single”引号的字符串“
    ,该字符串用引号解释,因此
    “single”引号的“regex”引号将丢失其引号,因为它是一个带引号的字符串。这有意义吗?请参阅:管道在makefiles中不是特殊字符,但在GNU make前提条件列表中除外,在该列表中,管道将普通前提条件与仅订购的前提条件分开。它们对shell来说是特殊的,但不是内部引号(任何一种类型)。感谢您的详细解释。printf的整个要点都是为了调试,所以我特别感谢有人评论说“@”隐藏了我想要得到的确切信息。