red*_*pet 4 scripting bash array shell-script case
是否可以使用case?检查变量是否包含在数组中?我想做类似的事情
ARR=( opt1 opt2 opt3 );
case $1 in
$ARR)
echo "Option is contained in the array";
*)
echo "Option is not contained in the array";
esac
Run Code Online (Sandbox Code Playgroud)
有了ksh93,由于这个错误,你可以这样做:
IFS='|'
ARR=( opt1 opt2 opt3 )
IFS='|'
case $1 in
(@("${ARR[*]}"))
echo "Option is contained in the array";;
(*)
echo "Option is not contained in the array";;
esac
Run Code Online (Sandbox Code Playgroud)
(我不会依赖它,因为该错误可能会在未来得到修复)。
使用zsh,您可以执行以下操作:
case ${ARR[(Ie)$1]}
(0)
echo "Option is not contained in the array";;
(*)
echo "Option is contained in the array";;
esac
Run Code Online (Sandbox Code Playgroud)
(不过,您可能更愿意在if ((ARR[(Ie)$1])); then echo is present...这里使用而不是 case 构造)。
${array[(I)pattern]}返回与数组中的模式匹配的最后一个元素的索引,否则返回 0。该e标志用于精确匹配(与模式匹配相反)。
使用bash, ksh, yash, zsh,如果您准备好假设$ARR并且$1不包含某个字符,例如@,并且$ARR不会为空,您可以执行以下操作:
IFS=@
case "@${ARR[*]}@" in
(*"@$1@"*)
echo "Option is contained in the array";;
(*)
echo "Option is not contained in the array";;
esac
Run Code Online (Sandbox Code Playgroud)
使用bash -O extglob, zsh -o kshglob -o globsubst,您可以定义一个帮助器,它根据数组的元素构建一个模式:
arraypat() {
awk '
BEGIN{
if (ARGC <= 1) print "!(*)"
else {
for (i = 1; i < ARGC; i++) {
gsub(/[][|<>\\?*()]/, "[&]", ARGV[i])
s = s sep ARGV[i]
sep = "|"
}
print "@(" s ")"
}
}' "$@"
}
case $1 in
($(arraypat "${ARR[@]}"))
echo "Option is contained in the array";;
(*)
echo "Option is not contained in the array";;
esac
Run Code Online (Sandbox Code Playgroud)
并不是真正以紧凑且易于使用的方式。请记住,在您的示例中$ARR,它将仅扩展到数组的第一个元素opt1。
您可以使用"${ARR[@]}",但是使用您的数据可能会给字符串带来误报1 opt。
对于更新版本的bash,您可以考虑使用关联数组:
declare -A arr
arr=( [opt1]=1 [opt2]=1 [opt3]=1 )
if [[ "${arr[$1]}" -eq 1 ]]; then
# $1 is a key in arr
else
# is not
fi
Run Code Online (Sandbox Code Playgroud)