
Suponha que eu tenha várias tarefas em segundo plano em execução, mas agora quero executar mais duas tarefas em segundo plano, mas espero apenas pelas duas últimas. Por exemplo:
# long running commands
sleep 60 &
sleep 60 &
# now wait only for these two:
sleep 5 & sleep 5 & wait; echo waited only for the 5s sleeps.
O resultado do comando acima é que o comando echo espera 60s.
Eu sei que possopasse um pid ou jobid para esperar. Mas como estou iniciando os processos em for
loop, não consigo obter os PIDs facilmente.
Eu tentei isso, mas sem sorte:
{ sleep 3 & sleep 5 & } wait; echo did not wait :
sleep 10 & { sleep 3 ; sleep 3 ; }& wait %2; echo only wait 3s
PS: Esta questão é uma extensão deesta pergunta mais simples.
Responder1
Você poderia iniciar um subshell:
{ sleep 20 && echo second output ; }
( sleep 2 & wait && echo first output )
O wait
comando no subshell só será válido lá.
Responder2
Com base nas orientações de @Kusalananda na pergunta mais simples, criei este exemplo. Talvez não seja o mais simples...
Todo o código abaixo está em um shell interativo. Eu apenas o dividi em partes para obter a resposta porque, caso contrário, seria difícil de ler.
Esteja ciente de que na bash
versão 4.1 e anteriores, o !
no ""
, aciona a substituição do histórico em um shell interativo (isso foi corrigido na versão 4.2). Foi por isso que eu estava sendo enganado. Se você realmente deseja citar, $!
você pode usar "$! "
e o espaço à direita impedirá que a substituição do histórico seja iniciada.
unset to_wait;
date;
sleep 3 &
for i in 1 2 3; do
sleep 1 &
# Don't put the ! in "" or you'll get an `event`.
to_wait+=( $! );
done;
wait "${to_wait[@]}";
date;
echo waited 1s for inner processes;
# wait for the rest of the processes (just for illustration)
wait;
date;
echo waited 3s for outer process;