Eu tenho um problema em um dos meus scripts de shell. Perguntei a alguns colegas, mas todos eles apenas balançaram a cabeça (depois de alguns arranhões), então eu vim aqui para uma resposta.
De acordo com o meu entendimento, o seguinte script shell deve imprimir "Count is 5" como a última linha. Exceto que não. Imprime "Contagem é 0". Se o "while read" for substituído por qualquer outro tipo de loop, ele funcionará perfeitamente. Aqui está o script:
eco "1"> input.data eco "2" >> input.data eco "3" >> input.data eco "4" >> input.data eco "5" >> input.data CNT = 0 cat input.data | enquanto lê; Faz deixe CNT ++; eco "Contando até $ CNT" feito eco "Contagem é $ CNT"
Por que isso acontece e como posso evitá-lo? Eu tentei isso no Debian Lenny e Squeeze, o mesmo resultado (por exemplo, bash 3.2.39 e bash 4.1.5. Admito totalmente que não sou um assistente de script de shell, para que qualquer ponteiro seja apreciado.
Este é um tipo de erro "comum". Os pipes criam SubShells, portanto, eles
while read
são executados em um shell diferente do seu script, que faz com que suaCNT
variável nunca seja alterada (apenas aquela dentro do subshell de pipe).Agrupe o último
echo
com o subshellwhile
para consertá-lo (há muitas outras maneiras de consertá-lo, esse é um. As respostas de Iain e Ignacio têm outras.)Explicação longa:
CNT
em seu script o valor 0;|
parawhile read
;$CNT
variável é exportada para o SubShell com o valor 0;CNT
valor para 5;echo
seuCNT
valor original de 0.fonte
Isso funciona
fonte
let CNT++
que deveria serCNT="$((CNT+1))"
usada para expansão aritmética compatível com POSIX . O resto já é portátil.Tente passar os dados em um sub-shell, como se fosse um arquivo antes do loop while. Isso é semelhante à solução de lain, mas assume que você não deseja um arquivo intermitente:
fonte