2010-12-08 8 views

Répondre

1

Essayer d'éviter des outils complexes:

test_array=('AA' 'BB' 'CC' 'D D' 'EE') 
OLD_IFS="$IFS" 
IFS=" 
" 
element=$(grep -n '^D D$' <<< "${test_array[*]}" | cut -d ":" -f 1) 
IFS="$OLD_IFS" 
echo $element 

Cependant, il consomme 2 processus. Si nous nous permettons sed, nous pourrions le faire avec un seul processus:

test_array=('AA' 'BB' 'CC' 'D D' 'EE') 
OLD_IFS="$IFS" 
IFS=" 
" 
element=$(sed -n -e '/^D D$/=' <<< "${test_array[*]}") 
IFS="$OLD_IFS" 
echo $element 

Mise à jour:

Comme indiqué par thkala dans les commentaires, cette solution est divisée en 3 cas. Veillez à ne pas l'utiliser si:

  1. Vous souhaitez un décalage indexé nul.
  2. Vous avez des retours à la ligne dans vos éléments de tableau.
  3. Et vous avez un tableau clairsemé, ou avez d'autres clés que des entiers.
+0

Ceci est cassé à deux égards: 1. il a une erreur par un, puisque les tableaux de bash sont basés sur zéro - bien que l'OP souhaite également un index basé sur un seul. 2. il suppose que les index de tableau sont contigus, alors qu'ils ne le sont pas - il se cassera complètement s'il y a des lacunes dans les affectations d'index de tableau ou si certains éléments ont été mis à 0 ... – thkala

+0

Oh, ça va aussi casser si n'importe quel tableau les éléments contiennent les nouvelles lignes ... – thkala

+0

Vraie, vraie et vraie: Aoutch! Je vais essayer de me rappeler que les tableaux de bash sont vraiment des cartes. Mais comme l'affiche semble aimer la réponse, je ne vais pas la supprimer, mais je vais la mettre à jour pour souligner les limites que vous avez trouvées. – jfg956

6
#!/bin/bash 

A=(AA BB CC DD EE) 

for i in "${!A[@]}"; do 
     if [[ "${A[i]}" = "$1" ]]; then 
       echo "$i" 
     fi 
done 

Notez la notation "${!A[@]}" qui donne la liste des index valides dans le tableau. En général, vous ne pouvez pas passer de 0 à "${#A[@]}" - 1, car les index ne sont pas nécessairement contigus. Il peut y avoir des écarts dans la plage d'index s'il y a des lacunes dans les affectations d'éléments de tableau ou si certains éléments ont été désactivés.

Le script ci-dessus affichera tous les index du tableau dont le contenu est égal au premier argument de ligne de commande du script.

EDIT:

Dans votre question, vous semblez vouloir le résultat comme un indice de tableau basé sur un. Dans ce cas, vous pouvez juste augmenter le résultat par:

#!/bin/bash 

A=(AA BB CC DD EE) 

for i in "${!A[@]}"; do 
     if [[ "${A[i]}" = "$1" ]]; then 
       let i++; 

       echo "$i" 
     fi 
done 

Gardez à l'esprit, cependant, que cet indice devra être décrémenté avant d'être utilisé avec un tableau de base zéro.

1

Boucle sur l'ensemble et maintien de la position. Lorsque vous trouvez l'élément correspondant à l'argument d'entrée, imprimez la position de l'élément. Vous devez en ajouter un à la position, car les tableaux ont une indexation basée sur zéro.

#! /bin/sh 
arg=$1 
echo $arg 
test_array=('AA' 'BB' 'CC' 'DD' 'EE') 
element_count=${#test_array[@]} 
index=0 

while [ $index -lt $element_count ] 
do  
    if [ "${test_array[index]}" = "$arg" ] 
    then 
    echo $((index+1)) 
    break 
    fi 
    ((index++)) 
done 
1

Sans boucle:

#!/bin/bash 

index() { 
    local IFS=$'\n'; 
    echo "${*:2}" | awk '$0 == "'"${1//\"/\\\"}"'" { print NR-1; exit; }' 
} 

array=("D A D" "A D" bBb "D WW" D "\" D \"" e1e " D " E1E D AA "" BB) 
element=${array[5]} 
index "$element" "${array[@]}" 

Sortie:

5