最简单的方法来检查数组中的索引或键?

使用:

set -o nounset 

1)有一个索引数组,如:

 myArray=( "red" "black" "blue" ) 

哪个是检查元素1是否被设置的最短path?
我有时使用以下内容:

 test "${#myArray[@]}" -gt "1" && echo "1 exists" || echo "1 doesn't exist" 

我想知道是否有首选。

2)如何处理不连续的索引?

 myArray=() myArray[12]="red" myArray[51]="black" myArray[129]="blue" 

如何快速检查“51”已经被设置为例子?

3)如何处理关联数组?

 declare -A myArray myArray["key1"]="red" myArray["key2"]="black" myArray["key3"]="blue" 

如何快速检查“key2”已被使用为例?

谢谢

EDITED
最简单的方法似乎是:

 if test "${myArray['key_or_index']+isset}" then echo "yes" else echo "no" fi; 

这适用于索引和关联数组。 没有错误显示与set -o数据集。
感谢doubleDown的headup。

检查元素是否设置(适用于索引和关联数组)

 [ ${array[key]+abc} ] && echo "exists" 

基本上${array[key]+abc}是做什么的

  • 如果array[key]被设置,则返回abc
  • 如果array[key]没有设置,则不返回任何内容

参考文献:

  1. 请参阅Bash手册中的参数扩展和小提示

    如果省略了冒号,操作员只testing[ 参数 ]

  2. 这个答案实际上是从这个SO问题的答案改编的: 如何判断一个string是不是在bash shell脚本中定义的 ?


包装函数:

 exists(){ if [ "$2" != in ]; then echo "Incorrect usage." echo "Correct usage: exists {key} in {array}" return fi eval '[ ${'$3'[$1]+muahaha} ]' } 

例如

 if ! exists key in array; then echo "No such array element"; fi 

不幸的是,bash没有办法在空的未定义的variables之间做出区别。

但有一些方法:

 $ array=() $ array[12]="red" $ array[51]="black" $ array[129]="blue" $ echo ${array[@]} red black blue $ echo ${!array[@]} 12 51 129 $ echo "${#array[@]}" 3 $ printf "%s\n" ${!array[@]}|grep -q ^51$ && echo 51 exist 51 exist $ printf "%s\n" ${!array[@]}|grep -q ^52$ && echo 52 exist 

(不答复)

而对于关联数组,你可以使用相同的:

 $ unset array $ declare -A array $ array["key1"]="red" $ array["key2"]="black" $ array["key3"]="blue" $ echo ${array[@]} blue black red $ echo ${!array[@]} key3 key2 key1 $ echo ${#array[@]} 3 $ set | grep ^array= array=([key3]="blue" [key2]="black" [key1]="red" ) $ printf "%s\n" ${!array[@]}|grep -q ^key2$ && echo key2 exist || echo key2 not exist key2 exist $ printf "%s\n" ${!array[@]}|grep -q ^key5$ && echo key5 exist || echo key5 not exist key5 not exist 

你可以在不需要外部工具的情况下完成这个工作(没有printf | grep作为纯bash ),为什么不呢,把checkIfExist()作为一个新的bash函数:

 $ checkIfExist() { eval 'local keys=${!'$1'[@]}'; eval "case '$2' in ${keys// /|}) return 0 ;; * ) return 1 ;; esac"; } $ checkIfExist array key2 && echo exist || echo don\'t exist $ checkIfExist array key5 && echo exist || echo don\'t don't 

甚至创build一个新的getIfExist bash函数,返回所需的值,如果需要的话不存在,则返回错误的结果代码:

 $ getIfExist() { eval 'local keys=${!'$1'[@]}'; eval "case '$2' in ${keys// /|}) echo \${$1[$2]};return 0 ;; * ) return 1 ;; esac"; } $ getIfExist array key1 red $ echo $? 0 $ # now with an empty defined value $ array["key4"]="" $ getIfExist array key4 $ echo $? 0 $ getIfExist array key5 $ echo $? 1 

testing在bash 4.3.39(1) – 释放

 declare -A fmap fmap['foo']="boo" key='foo' # should echo foo is set to 'boo' if [[ -z "${fmap[${key}]}" ]]; then echo "$key is unset in fmap"; else echo "${key} is set to '${fmap[${key}]}'"; fi key='blah' # should echo blah is unset in fmap if [[ -z "${fmap[${key}]}" ]]; then echo "$key is unset in fmap"; else echo "${key} is set to '${fmap[${key}]}'"; fi 

从人情节,条件expression式:

 -v varname True if the shell variable varname is set (has been assigned a value). 

例:

 declare -A foo foo[bar]="this is bar" foo[baz]="" if [[ -v "foo[bar]" ]] ; then echo "foo[bar] is set" fi if [[ -v "foo[baz]" ]] ; then echo "foo[baz] is set" fi if [[ -v "foo[quux]" ]] ; then echo "foo[quux] is set" fi 

这将显示foo [bar]和foo [baz]都被设置(尽pipe后者被设置为空值)并且foo [quux]不是。

我写了一个函数来检查一个键是否存在于Bash中的一个数组中:

 # Check if array key exists # Usage: array_key_exists $array_name $key # Returns: 0 = key exists, 1 = key does NOT exist function array_key_exists() { local _array_name="$1" local _key="$2" local _cmd='echo ${!'$_array_name'[@]}' local _array_keys=($(eval $_cmd)) local _key_exists=$(echo " ${_array_keys[@]} " | grep " $_key " &>/dev/null; echo $?) [[ "$_key_exists" = "0" ]] && return 0 || return 1 } 

 declare -A my_array my_array['foo']="bar" if [[ "$(array_key_exists 'my_array' 'foo'; echo $?)" = "0" ]]; then echo "OK" else echo "ERROR" fi 

testing与GNU bash,版本4.1.5(1) – 发行(i486-pc-linux-gnu)

这是我为脚本find的最简单的方法。

<search>是要查找的string, ASSOC_ARRAY是保存关联数组的variables的名称。

取决于你想达到的目标:

密钥存在

 if grep -qe "<search>" <(echo "${!ASSOC_ARRAY[@]}"); then echo key is present; fi 

键不存在

 if ! grep -qe "<search>" <(echo "${!ASSOC_ARRAY[@]}"); then echo key not present; fi 

价值存在

 if grep -qe "<search>" <(echo "${ASSOC_ARRAY[@]}"); then echo value is present; fi 

价值不存在

 if ! grep -qe "<search>" <(echo "${ASSOC_ARRAY[@]}"); then echo value not present; fi