Quero acessar a variável de índice de array enquanto faço um loop por meio de um array em meu script bash shell.
myscript.sh
#!/bin/bash AR=("foo" "bar" "baz" "bat") for i in ${AR[*]}; do echo $i done
O resultado do script acima é:
foo bar baz bat
O resultado que procuro é:
0 1 2 3
Como altero meu script para conseguir isso?
Comentários
Resposta
Você pode fazer isso usando Lista de chaves de array . Da bash
página do manual:
${!name[@]}
${!name[*]}
Lista de chaves da matriz . Se o nome for uma variável de array, expande-se para a lista de índices de array (chaves) atribuídos em nome. Se o nome não for um array, expande-se para
0
se o nome for definido e nulo caso contrário. Quando@
é usado e a expansão aparece entre aspas duplas, cada chave se expande para uma palavra separada.
Para seu exemplo:
#!/bin/bash AR=("foo" "bar" "baz" "bat") for i in "${!AR[@]}"; do printf "${AR[%s]}=%s\n" "$i" "${AR[i]}" done
Isso resulta em:
${AR[0]}=foo ${AR[1]}=bar ${AR[2]}=baz ${AR[3]}=bat
Observe que também trabalhar para índices não sucessivos:
#!/bin/bash AR=([3]="foo" [5]="bar" [25]="baz" [7]="bat") for i in "${!AR[@]}"; do printf "${AR[%s]}=%s\n" "$i" "${AR[i]}" done
Isso resulta em:
${AR[3]}=foo ${AR[5]}=bar ${AR[7]}=bat ${AR[25]}=baz
Comentários
- Embora essa resposta atinja o resultado desejado, ela é desnecessariamente ofuscada pela instrução printf. Por exemplo:
printf "$i=(${AR[i]})\n"
ouecho "$i=(${ARi]})"
ambos fornecem um pouco mais, mostrando como obter a chave & var, mas estritamente falandoecho "$i"
teria respondido ao OP. O resto é " bash fu " 🙂 - Por que não é possível:
a=(1 2);echo ${a[0]} # result: 1
?
Resposta
Além da resposta de jordanm, você também pode fazer uma C
como loop em bash
:
for ((idx=0; idx<${#array[@]}; ++idx)); do echo "$idx" "${array[idx]}" done
Comentários
- Somente se não for uma matriz esparsa …
Resposta
você pode fazer algo assim:
#!/bin/bash AR=("foo" "bar" "baz" "bat") length=${#AR[@]} for (( i = 0; i < length; i++ )); do echo "$i" done
saída:
0 1 2 3
Comentários
- O que isso significa que a resposta de pfnuesel ainda não diz?
- Posso estar enganado, mas a resposta de pfnuesels não reavalia o comprimento do array em cada iteração?
"${array[*]}"
em vez de"${array[@]}"
. Usar*
em vez de@
mais ou menos trata-o como uma string em vez de uma matriz.