【发布时间】:2020-05-25 06:20:07
【问题描述】:
我有两个 shell 脚本(Linux,#!/bin/bash),一个有一些常用的功能来查找文本等,另一个利用常用的功能做一些“实际”的工作。
在检查数组变量(test2.sh 内的oranges)以测试/查看它是否是一个数组(declare -p oranges 2>/dev/null | grep -q '^declare \-a' && printf "$fmt" "oranges is an indexed array")时,我偶然发现另一个数组(LINES 内test1.sh)突然得到带有随机数的“污染”。
我不明白为什么会这样。有人有答案吗?
如果您在使用脚本时使用 echo 或 printf ,则只有当您将错误传递到 2>/dev/null 并 grep 输出时,它才会产生零差异。我已将脚本缩减为基本要素以显示问题。
此外,通过将单行分开并将每个部分的输出分配给一个变量(参见test3.sh),这个问题很容易解决,所以我不会被困在脚本编写或进一步的进展上。我一直试图回答为什么会发生LINES 的污染。
test1.sh
#!/bin/bash
declare -a LINES
echo "::: DECLARE ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
test2.sh
#!/bin/bash
source ./test1.sh
declare -a oranges=()
echo "::: test2-1 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
declare -p oranges 2>/dev/null
echo "::: test2-2 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
declare -p oranges 2>/dev/null | grep -E -i '^declare \-a'
echo "::: test2-3 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
declare -p oranges 2>/dev/null | grep -E -i '^declare \-a' && printf "$fmt" "oranges is an indexed array"
echo "::: test2-4 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
declare -p LINES
declare -p oranges 2>/dev/null | grep -E -i '^declare \-a' && printf "$fmt" "oranges is an indexed array" || printf "$fmt" "oranges is not an indexed array"
echo "::: test2-5 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
declare -p oranges 2>/dev/null
echo "::: test2-6 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
并且在运行时会出现以下输出:
::: DECLARE ::: Length of [LINES] is: 0, :::Content of [LINES] is:
::: test2-1 ::: Length of [LINES] is: 0, :::Content of [LINES] is:
declare -a oranges=()
::: test2-2 ::: Length of [LINES] is: 0, :::Content of [LINES] is:
declare -a oranges=()
::: test2-3 ::: Length of [LINES] is: 1, :::Content of [LINES] is: 81
declare -a oranges=()
::: test2-4 ::: Length of [LINES] is: 1, :::Content of [LINES] is: 81
declare -a LINES=([0]="81")
declare -a oranges=()
::: test2-5 ::: Length of [LINES] is: 1, :::Content of [LINES] is: 81
declare -a oranges=()
::: test2-6 ::: Length of [LINES] is: 1, :::Content of [LINES] is: 81
test3.sh - 解决方法
#!/bin/bash
source ./test1.sh
declare -a oranges=()
echo "::: test2-1 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
someResult="$(declare -p oranges 2>/dev/null)"
thePattern="^declare \-a"
nextResult=`grep -E -i "$thePattern" <<< "$someResult"` || nextResult=""
if [[ -n "$nextResult" ]]
then
echo "oranges is an indexed array"
else
echo "oranges is NOT an indexed array"
fi
echo "::: test2-2 ::: Length of [LINES] is: ${#LINES[@]}, :::Content of [LINES] is: ${LINES[@]}"
test3.sh 的输出 ..
$ ./test3.sh
::: DECLARE ::: Length of [LINES] is: 0, :::Content of [LINES] is:
::: test2-1 ::: Length of [LINES] is: 0, :::Content of [LINES] is:
oranges is an indexed array
::: test2-2 ::: Length of [LINES] is: 0, :::Content of [LINES] is:
【问题讨论】:
-
我注意到在您奇怪的输出(“错误”情况)中,我们从未看到文本 _oranges 是一个索引数组_,尽管这应该被打印出来,不是吗?