Acrescentando ao mesmo array em vários loops, apenas os últimos valores permanecem Bash 4

6

Eu tenho algo assim:

FILES=()
for i in *.map
do
    FILES+=($i)
done

find /var/candy -name "chocolate_[0-9]" | while read snack
do
    FILES+=($snack)
done

for file in ../out/amsterdam/apples/{system.map,vmlinux}
do
    FILES+=($file)
done

Mas a matriz acaba contendo apenas ../out/amsterdam/apples/system.map e ../out/amsterdam/apples/vmlinux . O que aconteceu com os outros valores? Eu sei que eles existem nesses loops porque eu fiz eco para ter certeza de que as variáveis continham algo.

    
por Gregg Leventhal 08.11.2013 / 17:44

1 resposta

12

Extraído do FAQ do Bash :

I set variables in a loop that's in a pipeline. Why do they disappear after the loop terminates?

The reason for this potentially surprising behaviour, as described above, is that each SubShell introduces a new variable context and environment. The while loop above is executed in a new subshell with its own copy of the variable linecount created with the initial value of '0' taken from the parent shell. This copy then is used for counting. When the while loop is finished, the subshell copy is discarded, and the original variable linecount of the parent (whose value hasn't changed) is used in the echo command.

Para evitar que um subshell seja criado em seu segundo loop, você pode enviar dados para ele de maneiras diferentes de um pipe:

while read snack; do
    FILES+=($snack)
done < <(find /var/candy -name "chocolate_[0-9]")

.

while read snack; do
    FILES+=($snack)
done <<<"$(find /var/candy -name "chocolate_[0-9]")"
    
por 08.11.2013 / 18:00