Aqui está a minha opinião sobre isso.
Prefiro não usar o loop for do bash se puder evitá-lo, pois isso leva tempo para ser executado. Se algo tiver que ser repetido, seja algo que foi escrito em uma linguagem de nível inferior ao script de shell.
function array_contains { # arrayname value
local -A _arr=()
local IFS=
eval _arr=( $(eval printf '[%q]="1"\ ' "\${$1[@]}") )
return $(( 1 - 0${_arr[$2]} ))
}
Isso funciona criando uma matriz associativa temporária _arr
, cujos índices são derivados dos valores da matriz de entrada. (Observe que matrizes associativas estão disponíveis no bash 4 e acima, portanto, essa função não funcionará nas versões anteriores do bash.) Definimos $IFS
para evitar a divisão de palavras no espaço em branco.
A função não contém loops explícitos, embora as etapas internas do bash na matriz de entrada sejam preenchidas printf
. O formato printf é usado %q
para garantir que os dados de entrada sejam escapados, de forma que possam ser usados com segurança como chaves de matriz.
$ a=("one two" three four)
$ array_contains a three && echo BOOYA
BOOYA
$ array_contains a two && echo FAIL
$
Observe que tudo o que essa função usa é incorporado ao bash, portanto, não há canais externos arrastando você para baixo, mesmo na expansão de comando.
E se você não gosta de usar eval
... bem, você é livre para usar outra abordagem. :-)