#!/bin/bash
# set -x # debug version
N=${1:-123}
n=${2:-45}
workers=${workers:-${3:-10}}
((workers < 1)) && ((workers = 1))
((workers > 20)) && ((workers = 20))
((min=100000000000000)) #set min to some garbage value
work() {
for i in ${*}; do
for (( j=1; j<=${n}; j++ )); do
val=$(/path/to/a.out)
val2=$(echo ${val} | bc)
(( val2 < min )) && (( min = val2 ));
done
echo ${min}
# # debug version
# echo ${i} ${j} ${min}
done
}
# --
arr=($(
seq ${N} | xargs -n$[N/workers + 1] | while read i; do
work ${i} &
done
wait
))
echo ${arr[*]}
# --
# # debug version
# seq ${N} | xargs -t -n$[N/workers + 1] | while read i; do
# work ${i} &
# done
# wait
Sempre use trabalhadores ao gerar um número parametrizado de processos e limite o número máximo de trabalhadores que podem gerar .
xargs -n | while read
é um meio simples de iterar listas em lotes.
seq
cria uma lista de números de 1 a N.
xargs -n
divide essa lista em N / trabalhadores + 1 lotes.
- por exemplo, N = 100 trabalhadores = 10 produzirá 10 linhas de até 11 números de 1 a 100.
while read i
lê cada linha de números.
work ${i} &
apenas chama a work
função com ${i}
lote de números.
Para depurar, adicionei o código de depuração comentado. Basta substituir o echo
com a versão de depuração e o código entre # --
com a versão de depuração e você poderá ver como ele funciona em lotes. Remova o comentário set -x
para uma saída de depuração mais detalhada que você pode querer redirecionar para um arquivo.
Basta executar a versão de depuração com parâmetros diferentes para ver como ela funciona:
parallel.sh 223 5 1
parallel.sh 223 5 5
parallel.sh 223 5 10
parallel.sh 223 5 20
Isenção de responsabilidade: este código não sincroniza o min
valor entre os processos de trabalho. Obter o valor mínimo não é um exercício horrível. Isso provavelmente fará:
parallel.sh 223 5 20 | tr ' ' '\n' | sort -n | head -1
Ou apenas adicione o mesmo ao próprio script:
echo ${arr[*]} | tr ' ' '\n' | sort -n | head -1