Bash 中的这段代码
s="There are seven pencil"
declare -A A
while IFS= read -rn1 a; do
[ -z "$a" ] || [ -n "${A[$a]}" ] && continue
printf %s "$a"
((A[$a]++)) # A[$a]=x
done <<<"$s"
echo
产生这条线
Ther a svn pcil
所有空格都打印出来。这种行为是否有记录或以任何其他方式预期?
不过,当((A[$a]++))
替换为时A[$a]=x
,输出更改为
Ther asvnpcil
所以这次只打印第一个空格。
有什么不同?
这是 GNU bash 版本 4.4.12(1)-release (x86_64-pc-linux-gnu) 中的。
还有第三个操作可以比较,即let "A[$a]=x"
.奇怪的是,它介于前两者之间。它生成带有所有空格的行,即。Ther a svn pcil
。但使用减少艾萨克的回答,它的行为类似于A[$a]=x
赋值:
$ unset A; declare -A A; let "A[' ']++"; declare -p A
declare -A A=([" "]="1" )
最终,我发送了一份错误报告。这是它的线程。
答案1
核心问题是使用算术来声明变量。
代替:
(( A[$a]++ ))
和
declare -A A["$a"]=1
并且重复的空格被删除。
在我看来,这是一个错误,空格无法创建变量:
$ declare -A A; (( A[" "]++ )); declare -p A
declare -A A
在我发布上述答案后解决您的编辑问题:
有什么不同?
赋值确实将变量声明为数组的一部分:
$ unset A; declare -A A; A[" "]=1 ; declare -p A
declare -A A=([" "]="1" )
而算术展开式失败做同样的事情:
$ unset A; declare -A A; (( A[" "]=1 )); declare -p A
declare -A A