以下数组表示每台Linux机器上的磁盘数
每个单个阵列都包括linux计算机上的磁盘数。
echo ${ARRAY_DISK_Quantity[*]}
4 4 4 4 2 4 4 4
识别所有数组值相等的简单方法是什么?
良好状态:
4 4 4 4 4 4 4 4
不良状态:
4 4 4 4 4 4 2 4
不良状态:
6 6 6 6 6 6 6 6 6 6 2 6 2
以下数组表示每台Linux机器上的磁盘数
每个单个阵列都包括linux计算机上的磁盘数。
echo ${ARRAY_DISK_Quantity[*]}
4 4 4 4 2 4 4 4
识别所有数组值相等的简单方法是什么?
良好状态:
4 4 4 4 4 4 4 4
不良状态:
4 4 4 4 4 4 2 4
不良状态:
6 6 6 6 6 6 6 6 6 6 2 6 2
Answers:
bash
+ GNU sort
+ GNU grep
解决方案:
if [ "${#array[@]}" -gt 0 ] && [ $(printf "%s\000" "${array[@]}" |
LC_ALL=C sort -z -u |
grep -z -c .) -eq 1 ] ; then
echo ok
else
echo bad
fi
英文说明:如果对数组的元素进行唯一排序只能得到一个元素,则打印“确定”。否则打印“坏”。
数组上打印有NUL字节,分隔每个元素,通过管道传递到GNU排序(依赖于-z
aka --zero-terminated
和-u
aka --unique
选项),然后传递给grep
(使用-z
aka --null-data
和-c
aka 选项--count
)以计数输出行。
与我以前的版本不同,我不能wc
在这里使用它,因为它要求输入行以换行符结尾...并在将无法使用NUL分隔符的目的之后使用sed
或tr
将sort
NUL 转换为换行符。 grep -c
做出合理的替代。
这是作为函数重写的同一件事:
function count_unique() {
local LC_ALL=C
if [ "$#" -eq 0 ] ; then
echo 0
else
echo "$(printf "%s\000" "$@" |
sort --zero-terminated --unique |
grep --null-data --count .)"
fi
}
ARRAY_DISK_Quantity=(4 4 4 4 2 4 4 4)
if [ "$(count_unique "${ARRAY_DISK_Quantity[@]}")" -eq 1 ] ; then
echo "ok"
else
echo "bad"
fi
sort -u
它不会返回唯一的元素,而是返回排序相同的每组元素中的一个。例如,ARRAY_DISK_Quantity=(① ②)
在GNU系统上说“ OK”,在该系统上语言环境通常决定这2个字符的排序相同。您需要LC_ALL=C sort -u
字节对字节的唯一性。
与zsh
:
if ((${#${(u)ARRAY_DISK_Quantity[@]}} == 1)); then
echo OK
else
echo not OK
fi
(u)
参数扩展标志在哪里,用于扩展唯一值。这样我们就得到了数组中唯一值的计数。
更换== 1
用<= 1
的是你要考虑一个空数组是确定。
使用ksh93
,您可以对数组进行排序,并检查第一个元素与最后一个元素相同:
set -s -- "${ARRAY_DISK_Quantity[@]}"
if [ "$1" = "${@: -1}" ]; then
echo OK
else
echo not OK
fi
使用ksh88或pdksh / mksh:
set -s -- "${ARRAY_DISK_Quantity[@]}"
if eval '[ "$1" = "${'"$#"'}" ]'; then
echo OK
else
echo not OK
fi
使用bash
,您可能需要循环:
unique_values() {
typeset i
for i do
[ "$1" = "$i" ] || return 1
done
return 0
}
if unique_values "${ARRAY_DISK_Quantity[@]}"; then
echo OK
else
echo not OK
fi
(可以与所有具有数组支持的类似Bourne的外壳一起使用(ksh,zsh,bash,yash))。
请注意,它为空数组返回OK。[ "$#" -gt 0 ] || return
如果不希望在函数的开头添加a 。
bash
?
typeset
说Obsolete. See `help declare'.
有没有你正在使用,而不是它的一个原因local
还是declare
?
typeset
是适用于所有4个shell的那个。它也是80年代初期来自ksh 的原始版本(bash在变量作用域类型设置和声明时大多复制了ksh88,但决定重命名typeset
declare
并进行typeset
别名声明)。
bash
+ awk
解决方案:
function get_status() {
arr=("$@") # get the array passed as argument
if awk 'v && $1!=v{ exit 1 }{ v=$1 }' <(printf "%d\n" "${arr[@]}"); then
echo "status: Ok"
else
echo "status: Bad"
fi
}
测试案例1:
ARRAY_DISK_Quantity=(4 4 4 4 4 2 4 4)
get_status "${ARRAY_DISK_Quantity[@]}"
status: Bad
测试案例2:
ARRAY_DISK_Quantity=(4 4 4 4 4 4 4 4)
get_status "${ARRAY_DISK_Quantity[@]}"
status: Ok
我还有另一个bash only解决方案,该解决方案也应该适用于字符串:
isarray.equal () {
local placeholder="$1"
local num=0
while (( $# )); do
if [[ "$1" != "$placeholder" ]]; then
num=1
echo 'Bad' && break
fi
shift
done
[[ "$num" -ne 1 ]] && echo 'Okay'
}
示范:
[root@JBSTEST001 ~]# ARRAY_DISK_Quantity=(4 4 4 4 2 4 4 4)
[root@JBSTEST001 ~]# isarray.equal "${ARRAY_DISK_Quantity[@]}"
Bad
[root@JBSTEST001 ~]# ARRAY_DISK_Quantity=(4 4 4 4 4 4 4 4)
[root@JBSTEST001 ~]# isarray.equal "${ARRAY_DISK_Quantity[@]}"
Okay
[root@JBSTEST001 ~]# ARRAY_DISK_Quantity=(four four four four two four four four)
[root@JBSTEST001 ~]# isarray.equal "${ARRAY_DISK_Quantity[@]}"
Bad
[root@JBSTEST001 ~]# ARRAY_DISK_Quantity=(four four four four four four four four)
[root@JBSTEST001 ~]# isarray.equal "${ARRAY_DISK_Quantity[@]}"
Okay
仅限bash解决方案(假设a
为ARRAY_DISK_Quantity
)
ttt=${a[0]}
res=0
for i in "${a[@]}"
do
let res+=$(if [ "$ttt" -ne "$i" ]; then echo 1; else echo 0; fi);
done
if [ "$res" -eq 0 ]
then
echo "ok"
else
echo "bad"
fi
if [ "$ttt" -ne "$i" ]; then res=1; break; fi;