鉴于 Bash Reference Manual在 3.5.3 Shell Parameter Expansion
部分说:
${!name[@]} ${!name[*]}
If name is an array variable, expands to the list of array indices (keys) assigned in name. If name is not an array, expands to 0 if name is set and null otherwise. When ‘@’ is used and the expansion appears within double quotes, each key expands to a separate word.
和
${parameter:-word}
If parameter is unset or null, the expansion of word is substituted. Otherwise, the value of parameter is substituted.
和
${parameter:+word}
If parameter is null or unset, nothing is substituted, otherwise the expansion of word is substituted.
有人可以向我解释以下扩展的输出吗:
$ bash --version
GNU bash, version 3.2.25(1)-release (x86_64-redhat-linux-gnu)
Copyright (C) 2005 Free Software Foundation, Inc.
$ cat hm.sh
p() {
printf "%-11s : f=%1s : " "$*" "$f"
eval printf \'%1s :\\n\' "$@"
}
p '$f'
p '${!f[@]}'
p '${!f[@]:-b}'
echo "echo: ${!f[@]:-b} :"
p '${!f[@]:+b}'
echo "echo: ${!f[@]:+b} :"
f=f
p '$f'
p '${!f[@]}'
p '${!f[@]:-b}'
echo "echo: ${!f[@]:-b} :"
p '${!f[@]:+b}'
echo "echo: ${!f[@]:+b} :"
f=t
p '$f'
p '${!f[@]}'
p '${!f[@]:-b}'
echo "echo: ${!f[@]:-b} :"
p '${!f[@]:+b}'
echo "echo: ${!f[@]:+b} :"
$ bash hm.sh
$f : f= : :
${!f[@]} : f= : :
${!f[@]:-b} : f= : b :
echo: b :
${!f[@]:+b} : f= : :
echo: :
$f : f=f : f :
${!f[@]} : f=f : 0 :
${!f[@]:-b} : f=f : f :
echo: f :
${!f[@]:+b} : f=f : b :
echo: b :
$f : f=t : t :
${!f[@]} : f=t : 0 :
${!f[@]:-b} : f=t : b :
echo: b :
${!f[@]:+b} : f=t : :
echo: :
这就是为什么相关变量的内容会改变${!name[@]:-default}
和${!name [@]:+alt}
当内容不改变 ${!name[@]}
扩展本身如何扩展时扩展?
最佳答案
在语法 ${!f[@]}
中,参数扩展被解析为“列出键”表达式,这是 规则的特定异常(exception)之一>{!
引入了一个间接级别。语法 ${!f[@]:-b}
与该模式不匹配(因为它以 :-b
结尾),所以 !
被解释为间接引用,因此它是 name 是 f
的值的变量,默认情况下正在测试值修饰符。
有趣的问题是,“[@]
在该表达式中修改了什么?”它似乎在修改 f
,当 f
是一个标量时它什么都不做,但当 f
是一个以上的数组时它会产生一个无效的名称元素;在这种情况下,似乎会发生默认值替换。
我最好的猜测是,这是一个未记录且可能是无意的参数扩展极端情况。
关于bash 非数组 ${!name[@]} 参数扩展困惑,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27807615/