本文共 3100 字,大约阅读时间需要 10 分钟。
扩展bash
在Bash中,存储值的实体称为参数。 它们的值可以是具有常规语法的字符串或数组,也可以是整数或关联数组(当使用内置声明的特殊属性设置时)。 参数共有三种:位置参数,特殊参数和变量。
为了简洁起见,本文将重点介绍可用于字符串变量的几种扩展方法,尽管这些方法同样适用于其他类型的参数。
分配变量时,其名称必须仅由字母数字和下划线字符组成,并且不能以数字开头。 等号周围可能没有空格。 名称必须紧随其后,值紧随其后:
$ variable_1 = " my content "
将值存储在变量中仅在以后调用该值时才有用。 在Bash中,用其值替换参数引用称为扩展。 要扩展参数,只需在名称前加上$字符,然后可以选择将该名称括在大括号中:
$ echo $ variable_1 ${ variable_1 }my content my content
至关重要的是,如上面的示例所示,扩展发生在调用命令之前,因此命令从不会看到变量名,只有传递给它的文本作为扩展产生的参数。 此外,参数扩展发生在单词拆分之前 。 如果扩展结果包含空格,则在需要时应引用扩展名以保留参数完整性:
$ printf " %s \n " ${ variable_1 }mycontent$ printf " %s \n " " ${ variable_1 } "my content
但是,参数扩展远远超出了简单插值的范围。 在参数扩展的括号内,某些运算符及其参数可以放在名称之后,右括号之前。 这些运算符可以调用条件,子集,子字符串,替换,间接寻址,前缀列表,元素计数和大小写修改扩展方法,从而修改扩展结果。 除了重新分配运算符( =和:= )之外,这些运算符仅影响参数的扩展,而无需为后续扩展修改参数的值。
条件参数扩展允许分支该参数是未设置,为空还是具有内容。 根据这些条件,可以将参数扩展为其值,默认值或备用值。 抛出一个可定制的错误; 或将参数重新分配为默认值。 下表显示了条件参数扩展-每一行显示了使用运算符可能修改扩展的参数扩展,各列显示了给定参数状态的扩展结果,如列标题所示。 带有':'前缀的运算符会将空值的参数视为未设置的值。
parameter expansion | 未设定的变数 | var =“” | var =“ gnu” |
${var-default} | 默认 | - | 牛羚 |
${var:-default} | 默认 | 默认 | 牛羚 |
${var+alternate} | - | 备用 | 备用 |
${var:+alternate} | - | - | 备用 |
${var?error} | 错误 | - | 牛羚 |
${var:?error} | 错误 | 错误 | 牛羚 |
表中的=和:=运算符分别与-和:-相同,不同之处在于=变体将变量重新绑定到扩展结果。
例如,让我们尝试在由OUT_FILE变量指定的文件上打开用户的编辑器。 如果未指定EDITOR环境变量或OUT_FILE变量,则将出现问题。 使用条件扩展,我们可以确保当EDITOR变量扩展时,我们得到指定的值或至少一个理智的默认值:
$ echo ${ EDITOR }/usr/bin/vi$ echo ${ EDITOR :- $( which nano ) }/usr/bin/vi$ unset EDITOR$ echo ${ EDITOR :- $( which nano ) }/usr/bin/nano
在上面的基础上,如果未指定文件名,我们可以运行编辑器命令并在运行时因有用的错误而中止:
$ ${ EDITOR :- $( which nano ) } ${ OUT_FILE :? Missing filename }bash: OUT_FILE: Missing filename
可以通过偏移量或通过删除与模式匹配的内容,将参数扩展为仅其内容的一部分。 指定子字符串偏移量时,可以选择指定长度。 如果运行Bash 4.2或更高版本,则可以使用负数作为距字符串结尾的偏移量。 请注意在负偏移量周围使用了括号,以确保Bash不会将扩展解析为上面有条件的默认扩展运算符:
$ location = " CA 90095 "$ echo " Zip Code: ${ location : 3 } "Zip Code: 90095$ echo " Zip Code: ${ location : (-5) } "Zip Code: 90095$ echo " State: ${ location : 0 : 2 } "State: CA
提取子字符串的另一种方法是从与模式匹配的字符串中删除字符,或者使用#和##运算符从左侧删除字符,或者使用%和%运算符从右侧删除字符。 有用的助记符是#出现在注释的左侧, %出现在数字的右侧。 当运算符加倍时,它贪婪地匹配,而不是单个版本,后者删除了与模式匹配的最小字符集。
var =“ open source” | ||||
---|---|---|---|---|
parameter expansion | 偏移量5 长度4 | |||
${var:offset} | 资源 | |||
${var:offset:length} | 酸 | |||
* o的模式? | ||||
${var#pattern} | 来源 | |||
${var##pattern} | ce | |||
?e *的模式 | ||||
${var%pattern} | 酸味 | |||
${var%pattern} | Ø |
模式匹配与文件名匹配相同: *匹配零个或多个任何字符, ? 匹配任何字符的正好一个,[...]括号介绍针对单个字符的字符类的比赛,支撑否定(^),以及POSIX的字符类,例如[[:alnum:]]。 通过以这种方式从字符串中删除字符,我们可以获取子字符串而无需先知道所需数据的偏移量:
$ echo $ PATH/usr/local/bin:/usr/bin:/bin$ echo " Lowest priority in PATH: ${ PATH ## *: } "Lowest priority in PATH: /bin$ echo " Everything except lowest priority: ${ PATH % :* } "Everything except lowest priority: /usr/local/bin:/usr/bin$ echo " Highest priority in PATH: ${ PATH % :* } "Highest priority in PATH: /usr/local/bin
相同类型的模式用于参数扩展中的替换。 替换是通过/或//运算符引入的,后跟两个用另一个/分隔的参数,表示模式和要替换的字符串。 模式匹配始终是贪婪的,因此,在这种情况下,运算符的双精度版本会导致在变量的扩展中替换所有模式匹配项,而单例版本只会替换最左边的模式。
var =“免费开放” | ||||
---|---|---|---|---|
parameter expansion | [[:: space:]]的模式 _的字符串 | |||
${var/pattern/string} | 自由开放 | |||
${var//pattern/string} | 自由开放 |
丰富的参数扩展修饰符可将Bash变量和其他参数转换为简单的值存储之外的强大工具。 至少,了解Bash脚本时参数扩展的工作原理非常重要,但是我怀疑与我不同,你们中的许多人都会喜欢这些扩展修饰符带给脚本以及交互式会话的简洁性和表达性。 。
翻译自:
扩展bash
转载地址:http://myjzd.baihongyu.com/