bash 读取的 -d 选项如何工作?

the*_*fog 4 bash options shell-script quoting read

我有一个 bash 脚本,我试图在其中使用 read 将一个heredoc 字符串分配给一个变量,它只有在我read-d '' 选项一起使用时才有效,即

read -d '' <variable>
Run Code Online (Sandbox Code Playgroud)

脚本块

#!/usr/bin/env bash

function print_status() {
    echo
    echo "$1"
    echo 
}


read -d '' str <<- EOF
    Setup nginx site-config
    NOTE: if an /etc/nginx/sites-available config already exists for this
    website, this routine will replace existing config with template from
    this script. 
EOF

print_status "$str"
Run Code Online (Sandbox Code Playgroud)

在 SO 上找到了这个答案,这是我从中复制命令的地方,它有效,但为什么呢?我知道read当遇到第一个换行符时第一次调用停止,所以如果我使用一些没有出现在字符串中的字符,整个heredoc 都会被读入,例如

  • read -d '|' <variable> - 这有效
  • read -d'' <variable> ——这不

我确定这很简单,但是这个read -d ''命令选项是怎么回事?

Hau*_*ing 7

我想问题是为什么read -d ''有效但read -d''无效。

这个问题没有任何关系,read而是一个引用“问题”。阿""/''它是一个字符串(字)的一部分简单地根本不被识别。让 shell 向您展示看到/执行的内容:

start cmd:> set -x

start cmd:> echo read -d " " foo
+ echo read -d ' ' foo

start cmd:> echo read -d" " foo
+ echo read '-d ' foo

start cmd:> echo read -d "" foo
+ echo read -d '' foo

start cmd:> echo read -d"" foo
+ echo read -d foo
Run Code Online (Sandbox Code Playgroud)

  • 'read -d ''' 有点像 hack,这也是毫无价值的。您没有指定要查找的*任何*字符作为行尾(或者您可能正在查找空字符,ASCII 0,由于实现细节,该字符不能出现在字符串中),因此“read”始终只是读取到其输入的末尾,此时它以非零退出状态退出,因为它从未找到所请求的行结束字符。如果您希望“read”成功,例如使用“set -e”,这可能会成为一个问题。 (3认同)