Bash中[[表达式内$符号的省略、必用及可选场景问询
Bash中
[[表达式的$符号使用规则疑问 [[的求值规则和普通test([)差异显著,但bash手册并未对这些规则做出清晰说明。先看以下示例:
> a[1]='' > i=1 > [[ -v a[i] ]] && echo true || echo false true > [[ -v a[$i] ]] && echo true || echo false true > [[ -v a[$j] ]] && echo true || echo false false > i=0 > [[ -v a[$i] ]] && echo true || echo false false > [[ -v ${a[$i]} ]] && echo true || echo false false > i=1 > [[ -v ${a[$i]} ]] && echo true || echo false false
现正式询问:在[[表达式中,哪些场景可以省略$符号,哪些场景必须使用$符号,哪些场景使用$符号不影响结果正确性?
关于数组下标的求值规则
下标被视为必须求值为数字的算术表达式
在使用关联数组时,键似乎必须通过$符号展开。请看以下命令集:
> a[k]=k > declare -p a declare -a a=([0]="k") > declare -A A > A[k]=k > declare -p A declare -A A=([k]="k" ) > [[ -v a[k] ]] && echo true || echo false true > [[ -v A[k] ]] && echo true || echo false true > [[ -v a[j] ]] && echo true || echo false true > [[ -v A[j] ]] && echo true || echo false false > j=k > [[ -v a[j] ]] && echo true || echo false true > [[ -v A[j] ]] && echo true || echo false false > [[ -v A[$j] ]] && echo true || echo false true
场景分类说明
一、可以省略$符号的场景
- 普通数组(索引数组)的下标:在
[[的上下文里,普通数组的下标会被当作算术表达式自动求值,直接写变量名(不带$)会解析为变量的数值。比如[[ -v a[i] ]]等价于[[ -v a[$i] ]]。 - 算术比较场景:进行数值比较时,变量名无需加
$,会被当作算术表达式求值。比如[[ i -eq 1 ]]和[[ $i -eq 1 ]]效果完全一致。
二、必须使用$符号的场景
- 关联数组的键:关联数组的键是字符串类型,
[[里直接写变量名会被当作字面量字符串,而非变量的值。比如A[j]中的j是字符串"j",而非变量j的内容,必须写成A[$j]才能引用变量对应的键。 - 字符串比较中的变量引用:如果要拿变量的值做字符串比较,必须加
$。比如[[ $str == "hello" ]]才能正确引用变量str的值,不加$的话str会被当作字面量"str"处理。 - 数组元素值的引用:比如检查数组元素的值是否存在时,
${a[$i]}里的$不能省略,否则会被当作字面量字符串,而非数组元素的值。
三、使用$符号不影响结果正确性的场景
- 普通数组的下标:无论是
a[i]还是a[$i],在[[中都会被当作算术表达式求值,最终结果一致。 - 算术比较中的变量:带
$和不带$的变量在算术比较上下文里都会被正确求值,比如[[ $i -gt 0 ]]和[[ i -gt 0 ]]效果相同。
内容的提问来源于stack exchange,提问作者U. Windl
相关产品推荐
相关产品推荐

