转义和引号
转义和引号
Bash 只有一种数据类型,就是字符串。不管用户输入什么数据,Bash 都视为字符串。因此,字符串相关的引号和转义,对 Bash 来说就非常重要。
转义和反斜杠
某些字符在 Bash 里面有特殊含义(比如 $
、&
、*
)。Bash 在碰到这些字符的时候,会将其理解为其他意思,比如 $name
表示的是 name
这个变量,如果想要让 Bash 将其当作一个普通字符,不对其进行转义,就必须在这些特殊字符前面加上反斜杠,使其变成普通字符。这就加上反斜杠的操作叫做“转义”(escape)。
$ echo $name
$ echo *
aaa bbb ccc test.txt
$ echo \$name
$name
$ echo \*
*
因为 name 变量在当前环境没有定义,所以输出为空。
反斜杠本身也是特殊字符,想要输出反斜杠,也需要进行转义,\\
$ echo \\
\
反斜杠除了用于转义,还可以表示一些不可打印的字符。
\a
:响铃\b
:退格\n
:换行\r
:回车\t
:制表符
如果想要在命令行中让这些不可打印字符表达出其特殊含义,可以把它们放在引号里面,然后使用 echo
命令的 -e
参数。
$ echo a\tb
atb
$ echo "a\tb"
a\tb
$ echo -e "a\tb"
a b
$ echo -e "a\bb"
b
$ echo -e "a\nb"
a
b
换行符是一个特殊字符,表示命令的结束,Bash 收到这个字符以后,就会对输入的命令进行解释执行。换行符前面加上反斜杠转义,就使得换行符变成一个普通字符,即 \\n
,Bash 会将其当作长度为 0
的空字符处理,从而可以将一行命令写成多行。这也是为什么通过在命令的末尾写 \
可以将一行命令拆分成多行
$ echo hello \
> world \
> xiashuo.xyz
hello world xiashuo.xyz
单引号
Bash 允许字符串放在单引号或双引号之中,加以引用。
单引号用于保留字符的字面含义,各种特殊字符在单引号里面,都会变为普通字符,比如星号(*
)、美元符号($
)、反斜杠(\
)等。包括 Bash 模式扩展字符,在单引号中都会失效
$ echo '
由于反斜杠在单引号里面变成了普通字符,所以如果单引号之中,还要使用单引号,不能使用转义,需要在外层的单引号前面加上一个美元符号(`$`),然后再对里层的单引号转义。不过这种下,我们一般在双引号中使用单引号
```shell
$ echo 'it's'
> ^C
$ echo
## 双引号
双引号比单引号宽松,大部分特殊字符在双引号里面,都会失去特殊含义,变成普通字符,比如 `*`,这意味着,双引号里面不会进行文件名扩展。但是,三个特殊字符除外:美元符号(`$`)、反引号(`` ` ``)和反斜杠(`\`)。这三个字符在双引号之中,依然有特殊含义,会被 Bash 自动扩展。
在双引号中,美元符号用来引用变量,反引号则是执行子命令,反斜杠则是用来转义,以反斜杠开头的不可打印字符则会失效。
```shell
$ echo file{1..2}
file1 file2
$ echo "file{1..2}"
file{1..2}
$ echo "*"
*
$ echo "shell path: $SHELL"
shell path: /bin/bash
$ echo "date now : `date`"
date now : Mon Aug 14 17:19:14 CST 2023
$ echo "\"hello\" \"world\""
"hello" "world"
通过回车插入的换行符在双引号之中,会失去特殊含义,Bash 正常情况下会将换行符解释为命令结束,但是换行符在双引号之中就失去了这种特殊作用,只用来换行,所以可以输入多行。echo
命令会将换行符原样输出,显示的时候正常解释为换行。所以可以利用双引号,在命令行输入多行文本。
$ echo "hello
>
> world
> "
hello
world
但是你直接在双引号中手写 \n
是不行的
$ echo "hello\nworld"
hello\nworld
双引号的另一个常见的使用场合是,文件名包含空格。这时就必须使用双引号(或单引号),将文件名放在里面。否则 Bash 会将其理解为被被空格分割开的两个参数
双引号还有一个作用,就是保存原始命令的输出格式。
$ cal
August 2023
Su Mo Tu We Th Fr Sa
1 2 3 4 5
6 7 8 9 10 11 12
13 14 15 16 17 18 19
20 21 22 23 24 25 26
27 28 29 30 31
$ echo $(cal)
August 2023 Su Mo Tu We Th Fr Sa 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
$ echo "$(cal)"
August 2023
Su Mo Tu We Th Fr Sa
1 2 3 4 5
6 7 8 9 10 11 12
13 14 15 16 17 18 19
20 21 22 23 24 25 26
27 28 29 30 31
Here 文档
Here 文档(here document)是一种输入多行字符串的方法,格式如下:
<< token
text
token
它的格式分成开始标记(<< token
)和结束标记(token
)。开始标记是两个小于号加上 token,中间可以有空格也可以没有空格,token 可以随意取,后面必须是一个换行符;结束标记是单独一行顶格写的 token,如果不是顶格,结束标记不起作用。两者之间就是多行字符串的内容。
token 可以理解开始输入和结束输入的文本标记,阮一峰大佬说这是 Here 文档的名称,其实不合适
$ cat << file
> 111
> 222
> 333
> file
111
222
333
我们在 shell 脚本中创建文件并在其中填入内容的时候,经常使用 Here 文档。
$ cat > test.txt << _
> <html>
> <div>
> </div>
> </html>
> _
$ cat test.txt
<html>
<div>
</div>
</html>
在 Here 文档内部会发生变量解析,同时支持反斜杠转义,但是不支持通配符扩展,双引号和单引号也失去语法作用,变成了普通字符。
支持变量解析,让我们可以在脚本中根据变量动态地生成 Here 文档。
$ cat << EOF
> $name
> "$name"
> '$name'
> \$name
> *
> EOF
xiashuo.xyz
"xiashuo.xyz"
'xiashuo.xyz'
$name
*
如果不希望发生变量替换,可以把 Here 文档的开始标记放在单引号之中。(结束标记不用放到单引号中)
Here 文档的本质是重定向,它将文档重定向给了某个命令的标准输入,所以,Here 文档只适合那些可以接受标准输入作为参数的命令,比如 cat
、grep
,有的命令不接受标准输入作为参数,比如 echo
,所以 echo
命令无法配合 Here 文档。
关于标准输入跟命令行参数有什么区别,请看《Linux 文件系统基础》的
| 管道符号
小节
关于什么是重定向,请看《Linux 文件系统基础》的
>指令和>>指令
小节重定向和管道还是有区别的,阮一峰大佬的 博客 中写到重定向等同于管道的说法是错误的
此外,Here 文档也不能作为变量的值,只能用于命令的参数。
Here 字符串
Here 文档还有一个变体,叫做 Here 字符串(Here string),使用三个小于号(<<<
)表示。
<<< string
它的作用是将字符串通过标准输入,传递给命令。
有些命令直接接受给定的参数,与通过标准输入接受参数,结果是不一样的。所以才有了这个语法,使得将字符串通过标准输入传递给命令更方便,比如 cat
命令只接受标准输入传入的字符串。
$ cat hello world
cat: hello: No such file or directory
cat: world: No such file or directory
$ cat <<< 'hello world'
hello world
# 效果等同于 echo
$ echo hello world
hello world
效果等同于 echo hello world
$ echo '*'
*
$ echo '
$ echo '
$ echo ''
\
由于反斜杠在单引号里面变成了普通字符,所以如果单引号之中,还要使用单引号,不能使用转义,需要在外层的单引号前面加上一个美元符号(`$`),然后再对里层的单引号转义。不过这种下,我们一般在双引号中使用单引号
{{CODE_BLOCK_5}}
## 双引号
双引号比单引号宽松,大部分特殊字符在双引号里面,都会失去特殊含义,变成普通字符,比如 `*`,这意味着,双引号里面不会进行文件名扩展。但是,三个特殊字符除外:美元符号(`$`)、反引号(`` ` ``)和反斜杠(`\`)。这三个字符在双引号之中,依然有特殊含义,会被 Bash 自动扩展。
在双引号中,美元符号用来引用变量,反引号则是执行子命令,反斜杠则是用来转义,以反斜杠开头的不可打印字符则会失效。
{{CODE_BLOCK_6}}
通过回车插入的换行符在双引号之中,会失去特殊含义,Bash 正常情况下会将换行符解释为命令结束,但是换行符在双引号之中就失去了这种特殊作用,**只用来换行**,所以可以输入多行。`echo` 命令会将换行符原样输出,显示的时候正常解释为换行。所以可以利用双引号,在命令行输入多行文本。
{{CODE_BLOCK_7}}
但是你直接在双引号中手写 `\n` 是不行的
{{CODE_BLOCK_8}}
双引号的另一个常见的使用场合是,文件名包含空格。这时就必须使用双引号(或单引号),将文件名放在里面。否则 Bash 会将其理解为被被空格分割开的两个参数
双引号还有一个作用,就是保存原始命令的输出格式。
{{CODE_BLOCK_9}}
## Here 文档
Here 文档(here document)是一种输入多行字符串的方法,格式如下:
{{CODE_BLOCK_10}}
它的格式分成开始标记(`<< token`)和结束标记(`token`)。开始标记是两个小于号加上 token,中间可以有空格也可以没有空格,token 可以随意取,后面必须是一个换行符;结束标记是单独一行顶格写的 token,如果不是顶格,结束标记不起作用。两者之间就是多行字符串的内容。
> token 可以理解开始输入和结束输入的文本标记,阮一峰大佬说这是 Here 文档的名称,其实不合适
{{CODE_BLOCK_11}}
我们在 shell 脚本中创建文件并在其中填入内容的时候,经常使用 Here 文档。
{{CODE_BLOCK_12}}
在 Here 文档内部会发生变量解析,同时支持反斜杠转义,但是不支持通配符扩展,双引号和单引号也失去语法作用,变成了普通字符。
> 支持变量解析,让我们可以在脚本中根据变量动态地生成 Here 文档。
{{CODE_BLOCK_13}}
如果不希望发生变量替换,可以把 Here 文档的开始标记放在单引号之中。(结束标记不用放到单引号中)
Here 文档的本质是重定向,它将文档重定向给了某个命令的标准输入,所以,Here 文档只适合那些可以接受标准输入作为参数的命令,比如 `cat`、`grep`,有的命令不接受标准输入作为参数,比如 `echo`,所以 `echo` 命令无法配合 Here 文档。
> 关于标准输入跟命令行参数有什么区别,请看《Linux 文件系统基础》的 `| 管道符号` 小节
> 关于什么是重定向,请看《Linux 文件系统基础》的 `>指令和>>指令` 小节
>
> 重定向和管道还是有区别的,阮一峰大佬的 [博客](https://wangdoc.com/bash/quotation#here-%E6%96%87%E6%A1%A3) 中写到重定向等同于管道的说法是错误的
此外,Here 文档也不能作为变量的值,只能用于命令的参数。
## Here 字符串
Here 文档还有一个变体,叫做 Here 字符串(Here string),使用三个小于号(`<<<`)表示。
{{CODE_BLOCK_14}}
它的作用是将字符串通过标准输入,传递给命令。
**有些命令直接接受给定的参数,与通过标准输入接受参数,结果是不一样的**。所以才有了这个语法,使得将字符串通过标准输入传递给命令更方便,比如 `cat` 命令只接受标准输入传入的字符串。
{{CODE_BLOCK_15}}
效果等同于 `echo hello world`
it's'
> ^C
$ echo
## 双引号
双引号比单引号宽松,大部分特殊字符在双引号里面,都会失去特殊含义,变成普通字符,比如 `*`,这意味着,双引号里面不会进行文件名扩展。但是,三个特殊字符除外:美元符号(`$`)、反引号(`` ` ``)和反斜杠(`\`)。这三个字符在双引号之中,依然有特殊含义,会被 Bash 自动扩展。
在双引号中,美元符号用来引用变量,反引号则是执行子命令,反斜杠则是用来转义,以反斜杠开头的不可打印字符则会失效。
{{CODE_BLOCK_6}}
通过回车插入的换行符在双引号之中,会失去特殊含义,Bash 正常情况下会将换行符解释为命令结束,但是换行符在双引号之中就失去了这种特殊作用,**只用来换行**,所以可以输入多行。`echo` 命令会将换行符原样输出,显示的时候正常解释为换行。所以可以利用双引号,在命令行输入多行文本。
{{CODE_BLOCK_7}}
但是你直接在双引号中手写 `\n` 是不行的
{{CODE_BLOCK_8}}
双引号的另一个常见的使用场合是,文件名包含空格。这时就必须使用双引号(或单引号),将文件名放在里面。否则 Bash 会将其理解为被被空格分割开的两个参数
双引号还有一个作用,就是保存原始命令的输出格式。
{{CODE_BLOCK_9}}
## Here 文档
Here 文档(here document)是一种输入多行字符串的方法,格式如下:
{{CODE_BLOCK_10}}
它的格式分成开始标记(`<< token`)和结束标记(`token`)。开始标记是两个小于号加上 token,中间可以有空格也可以没有空格,token 可以随意取,后面必须是一个换行符;结束标记是单独一行顶格写的 token,如果不是顶格,结束标记不起作用。两者之间就是多行字符串的内容。
> token 可以理解开始输入和结束输入的文本标记,阮一峰大佬说这是 Here 文档的名称,其实不合适
{{CODE_BLOCK_11}}
我们在 shell 脚本中创建文件并在其中填入内容的时候,经常使用 Here 文档。
{{CODE_BLOCK_12}}
在 Here 文档内部会发生变量解析,同时支持反斜杠转义,但是不支持通配符扩展,双引号和单引号也失去语法作用,变成了普通字符。
> 支持变量解析,让我们可以在脚本中根据变量动态地生成 Here 文档。
{{CODE_BLOCK_13}}
如果不希望发生变量替换,可以把 Here 文档的开始标记放在单引号之中。(结束标记不用放到单引号中)
Here 文档的本质是重定向,它将文档重定向给了某个命令的标准输入,所以,Here 文档只适合那些可以接受标准输入作为参数的命令,比如 `cat`、`grep`,有的命令不接受标准输入作为参数,比如 `echo`,所以 `echo` 命令无法配合 Here 文档。
> 关于标准输入跟命令行参数有什么区别,请看《Linux 文件系统基础》的 `| 管道符号` 小节
> 关于什么是重定向,请看《Linux 文件系统基础》的 `>指令和>>指令` 小节
>
> 重定向和管道还是有区别的,阮一峰大佬的 [博客](https://wangdoc.com/bash/quotation#here-%E6%96%87%E6%A1%A3) 中写到重定向等同于管道的说法是错误的
此外,Here 文档也不能作为变量的值,只能用于命令的参数。
## Here 字符串
Here 文档还有一个变体,叫做 Here 字符串(Here string),使用三个小于号(`<<<`)表示。
{{CODE_BLOCK_14}}
它的作用是将字符串通过标准输入,传递给命令。
**有些命令直接接受给定的参数,与通过标准输入接受参数,结果是不一样的**。所以才有了这个语法,使得将字符串通过标准输入传递给命令更方便,比如 `cat` 命令只接受标准输入传入的字符串。
{{CODE_BLOCK_15}}
效果等同于 `echo hello world`
$
$ echo '$name'
$name
$ echo '*'
*
$ echo '$(ls)'
$(ls)
$ echo '$((2+2))'
$((2+2))
$ echo '\'
\
由于反斜杠在单引号里面变成了普通字符,所以如果单引号之中,还要使用单引号,不能使用转义,需要在外层的单引号前面加上一个美元符号($
),然后再对里层的单引号转义。不过这种下,我们一般在双引号中使用单引号
{{CODE_BLOCK_5}}
双引号
双引号比单引号宽松,大部分特殊字符在双引号里面,都会失去特殊含义,变成普通字符,比如 *
,这意味着,双引号里面不会进行文件名扩展。但是,三个特殊字符除外:美元符号($
)、反引号(`
)和反斜杠(\
)。这三个字符在双引号之中,依然有特殊含义,会被 Bash 自动扩展。
在双引号中,美元符号用来引用变量,反引号则是执行子命令,反斜杠则是用来转义,以反斜杠开头的不可打印字符则会失效。
{{CODE_BLOCK_6}}
通过回车插入的换行符在双引号之中,会失去特殊含义,Bash 正常情况下会将换行符解释为命令结束,但是换行符在双引号之中就失去了这种特殊作用,只用来换行,所以可以输入多行。echo
命令会将换行符原样输出,显示的时候正常解释为换行。所以可以利用双引号,在命令行输入多行文本。
{{CODE_BLOCK_7}}
但是你直接在双引号中手写 \n
是不行的
{{CODE_BLOCK_8}}
双引号的另一个常见的使用场合是,文件名包含空格。这时就必须使用双引号(或单引号),将文件名放在里面。否则 Bash 会将其理解为被被空格分割开的两个参数
双引号还有一个作用,就是保存原始命令的输出格式。
{{CODE_BLOCK_9}}
Here 文档
Here 文档(here document)是一种输入多行字符串的方法,格式如下:
{{CODE_BLOCK_10}}
它的格式分成开始标记(<< token
)和结束标记(token
)。开始标记是两个小于号加上 token,中间可以有空格也可以没有空格,token 可以随意取,后面必须是一个换行符;结束标记是单独一行顶格写的 token,如果不是顶格,结束标记不起作用。两者之间就是多行字符串的内容。
token 可以理解开始输入和结束输入的文本标记,阮一峰大佬说这是 Here 文档的名称,其实不合适
{{CODE_BLOCK_11}}
我们在 shell 脚本中创建文件并在其中填入内容的时候,经常使用 Here 文档。
{{CODE_BLOCK_12}}
在 Here 文档内部会发生变量解析,同时支持反斜杠转义,但是不支持通配符扩展,双引号和单引号也失去语法作用,变成了普通字符。
支持变量解析,让我们可以在脚本中根据变量动态地生成 Here 文档。
{{CODE_BLOCK_13}}
如果不希望发生变量替换,可以把 Here 文档的开始标记放在单引号之中。(结束标记不用放到单引号中)
Here 文档的本质是重定向,它将文档重定向给了某个命令的标准输入,所以,Here 文档只适合那些可以接受标准输入作为参数的命令,比如 cat
、grep
,有的命令不接受标准输入作为参数,比如 echo
,所以 echo
命令无法配合 Here 文档。
关于标准输入跟命令行参数有什么区别,请看《Linux 文件系统基础》的
| 管道符号
小节
关于什么是重定向,请看《Linux 文件系统基础》的
>指令和>>指令
小节重定向和管道还是有区别的,阮一峰大佬的 博客 中写到重定向等同于管道的说法是错误的
此外,Here 文档也不能作为变量的值,只能用于命令的参数。
Here 字符串
Here 文档还有一个变体,叫做 Here 字符串(Here string),使用三个小于号(<<<
)表示。
{{CODE_BLOCK_14}}
它的作用是将字符串通过标准输入,传递给命令。
有些命令直接接受给定的参数,与通过标准输入接受参数,结果是不一样的。所以才有了这个语法,使得将字符串通过标准输入传递给命令更方便,比如 cat
命令只接受标准输入传入的字符串。
{{CODE_BLOCK_15}}
效果等同于 echo hello world
it's'
it's
$ echo "it's"
it's
## 双引号
双引号比单引号宽松,大部分特殊字符在双引号里面,都会失去特殊含义,变成普通字符,比如 `*`,这意味着,双引号里面不会进行文件名扩展。但是,三个特殊字符除外:美元符号(`$`)、反引号(`` ` ``)和反斜杠(`\`)。这三个字符在双引号之中,依然有特殊含义,会被 Bash 自动扩展。
在双引号中,美元符号用来引用变量,反引号则是执行子命令,反斜杠则是用来转义,以反斜杠开头的不可打印字符则会失效。
{{CODE_BLOCK_6}}
通过回车插入的换行符在双引号之中,会失去特殊含义,Bash 正常情况下会将换行符解释为命令结束,但是换行符在双引号之中就失去了这种特殊作用,**只用来换行**,所以可以输入多行。`echo` 命令会将换行符原样输出,显示的时候正常解释为换行。所以可以利用双引号,在命令行输入多行文本。
{{CODE_BLOCK_7}}
但是你直接在双引号中手写 `\n` 是不行的
{{CODE_BLOCK_8}}
双引号的另一个常见的使用场合是,文件名包含空格。这时就必须使用双引号(或单引号),将文件名放在里面。否则 Bash 会将其理解为被被空格分割开的两个参数
双引号还有一个作用,就是保存原始命令的输出格式。
{{CODE_BLOCK_9}}
## Here 文档
Here 文档(here document)是一种输入多行字符串的方法,格式如下:
{{CODE_BLOCK_10}}
它的格式分成开始标记(`<< token`)和结束标记(`token`)。开始标记是两个小于号加上 token,中间可以有空格也可以没有空格,token 可以随意取,后面必须是一个换行符;结束标记是单独一行顶格写的 token,如果不是顶格,结束标记不起作用。两者之间就是多行字符串的内容。
> token 可以理解开始输入和结束输入的文本标记,阮一峰大佬说这是 Here 文档的名称,其实不合适
{{CODE_BLOCK_11}}
我们在 shell 脚本中创建文件并在其中填入内容的时候,经常使用 Here 文档。
{{CODE_BLOCK_12}}
在 Here 文档内部会发生变量解析,同时支持反斜杠转义,但是不支持通配符扩展,双引号和单引号也失去语法作用,变成了普通字符。
> 支持变量解析,让我们可以在脚本中根据变量动态地生成 Here 文档。
{{CODE_BLOCK_13}}
如果不希望发生变量替换,可以把 Here 文档的开始标记放在单引号之中。(结束标记不用放到单引号中)
Here 文档的本质是重定向,它将文档重定向给了某个命令的标准输入,所以,Here 文档只适合那些可以接受标准输入作为参数的命令,比如 `cat`、`grep`,有的命令不接受标准输入作为参数,比如 `echo`,所以 `echo` 命令无法配合 Here 文档。
> 关于标准输入跟命令行参数有什么区别,请看《Linux 文件系统基础》的 `| 管道符号` 小节
> 关于什么是重定向,请看《Linux 文件系统基础》的 `>指令和>>指令` 小节
>
> 重定向和管道还是有区别的,阮一峰大佬的 [博客](https://wangdoc.com/bash/quotation#here-%E6%96%87%E6%A1%A3) 中写到重定向等同于管道的说法是错误的
此外,Here 文档也不能作为变量的值,只能用于命令的参数。
## Here 字符串
Here 文档还有一个变体,叫做 Here 字符串(Here string),使用三个小于号(`<<<`)表示。
{{CODE_BLOCK_14}}
它的作用是将字符串通过标准输入,传递给命令。
**有些命令直接接受给定的参数,与通过标准输入接受参数,结果是不一样的**。所以才有了这个语法,使得将字符串通过标准输入传递给命令更方便,比如 `cat` 命令只接受标准输入传入的字符串。
{{CODE_BLOCK_15}}
效果等同于 `echo hello world`
$
$ echo '$name'
$name
$ echo '*'
*
$ echo '$(ls)'
$(ls)
$ echo '$((2+2))'
$((2+2))
$ echo '\'
\
由于反斜杠在单引号里面变成了普通字符,所以如果单引号之中,还要使用单引号,不能使用转义,需要在外层的单引号前面加上一个美元符号($
),然后再对里层的单引号转义。不过这种下,我们一般在双引号中使用单引号
{{CODE_BLOCK_5}}
双引号
双引号比单引号宽松,大部分特殊字符在双引号里面,都会失去特殊含义,变成普通字符,比如 *
,这意味着,双引号里面不会进行文件名扩展。但是,三个特殊字符除外:美元符号($
)、反引号(`
)和反斜杠(\
)。这三个字符在双引号之中,依然有特殊含义,会被 Bash 自动扩展。
在双引号中,美元符号用来引用变量,反引号则是执行子命令,反斜杠则是用来转义,以反斜杠开头的不可打印字符则会失效。
{{CODE_BLOCK_6}}
通过回车插入的换行符在双引号之中,会失去特殊含义,Bash 正常情况下会将换行符解释为命令结束,但是换行符在双引号之中就失去了这种特殊作用,只用来换行,所以可以输入多行。echo
命令会将换行符原样输出,显示的时候正常解释为换行。所以可以利用双引号,在命令行输入多行文本。
{{CODE_BLOCK_7}}
但是你直接在双引号中手写 \n
是不行的
{{CODE_BLOCK_8}}
双引号的另一个常见的使用场合是,文件名包含空格。这时就必须使用双引号(或单引号),将文件名放在里面。否则 Bash 会将其理解为被被空格分割开的两个参数
双引号还有一个作用,就是保存原始命令的输出格式。
{{CODE_BLOCK_9}}
Here 文档
Here 文档(here document)是一种输入多行字符串的方法,格式如下:
{{CODE_BLOCK_10}}
它的格式分成开始标记(<< token
)和结束标记(token
)。开始标记是两个小于号加上 token,中间可以有空格也可以没有空格,token 可以随意取,后面必须是一个换行符;结束标记是单独一行顶格写的 token,如果不是顶格,结束标记不起作用。两者之间就是多行字符串的内容。
token 可以理解开始输入和结束输入的文本标记,阮一峰大佬说这是 Here 文档的名称,其实不合适
{{CODE_BLOCK_11}}
我们在 shell 脚本中创建文件并在其中填入内容的时候,经常使用 Here 文档。
{{CODE_BLOCK_12}}
在 Here 文档内部会发生变量解析,同时支持反斜杠转义,但是不支持通配符扩展,双引号和单引号也失去语法作用,变成了普通字符。
支持变量解析,让我们可以在脚本中根据变量动态地生成 Here 文档。
{{CODE_BLOCK_13}}
如果不希望发生变量替换,可以把 Here 文档的开始标记放在单引号之中。(结束标记不用放到单引号中)
Here 文档的本质是重定向,它将文档重定向给了某个命令的标准输入,所以,Here 文档只适合那些可以接受标准输入作为参数的命令,比如 cat
、grep
,有的命令不接受标准输入作为参数,比如 echo
,所以 echo
命令无法配合 Here 文档。
关于标准输入跟命令行参数有什么区别,请看《Linux 文件系统基础》的
| 管道符号
小节
关于什么是重定向,请看《Linux 文件系统基础》的
>指令和>>指令
小节重定向和管道还是有区别的,阮一峰大佬的 博客 中写到重定向等同于管道的说法是错误的
此外,Here 文档也不能作为变量的值,只能用于命令的参数。
Here 字符串
Here 文档还有一个变体,叫做 Here 字符串(Here string),使用三个小于号(<<<
)表示。
{{CODE_BLOCK_14}}
它的作用是将字符串通过标准输入,传递给命令。
有些命令直接接受给定的参数,与通过标准输入接受参数,结果是不一样的。所以才有了这个语法,使得将字符串通过标准输入传递给命令更方便,比如 cat
命令只接受标准输入传入的字符串。
{{CODE_BLOCK_15}}
效果等同于 echo hello world