ループ内の反復回数が10 ^ 6のように非常に大きくなる可能性がある、forループを並列化したいと思います。ですから、プロセスよりもスレッドを作成できればもっと良いでしょう。どうやってするの?コードは次のとおりです
N=$1
for (( i=0; i < $N; i++ )); do
./random >> output /* in each iteration one random number is appended to
a file "output" */
done
random
プログラムが単一の数値を生成するだけの場合、あなたが本当に本当にそれでもこのようにしたいのなら、チャンクでそれをしてください:
for i in {0..9}; do
for ((j = 1; j < $N/10; j++)); do
./random
done > tmp$i &
pid[$i]=$?
done
for i in {0..9}; do
wait ${pid[$i]}
done
cat tmp{0..9} >> outfile
新しいスレッドを手動で作成できるシェルを私は知りません。通常、現在のシェルの既存のスレッドのみを利用できます(または、実際には新しいプロセスであるサブシェルを作成できます)。代わりにpython
または別の言語を使用してください。
できたとしても、この規模の何かにシェルスクリプトを使用することはお勧めしません。 10 ^ 6回の反復を実行すると、コンパイルされた言語と比較してパフォーマンスが大幅に低下する可能性があります。
いつものように、問題はリソースの競合です。同時に実行されるプロセス/スレッドの数を制限する必要があります。
また、並行スレッドを持つことは、実行される処理のタイプに大きく依存します。メモリ、CPU、I/Oなどのプログラミングが適切に組み合わされていると、はるかに優れています。すべてのサブプロセスがすべてのCPUを実行する場合、一度に10〜20を実行しても何も高速化されません。処理を他のマシンにファームアウトすることを試みることができます。例えばsshを使用して他のマシンで呼び出しを開始し、結果を取得します。
迅速で汚れた最初のパスは、次のようなものです。
N=$1 # max number to iterate on
shift # rest of command line is the command to run: e.g. "./random"
maxcount=10 # maximum in the pool
curcount=0 # how many currently in the pool
reaper () {
wait
curcount=`expr $curcount - 1`
}
spawnnext () {
n=$1
shift
while [ $curcount -ge $maxcount ]; do
sleep 1 # wait for a free slot in the pool
done
echo $n
"$@" &
curcount=`expr $curcount + 1`
}
trap 'reaper' CHLD
for (( i=0; i < $N; i++)); do
spawnnext $i "$@"
done
注意;私はこれをテストしていません。その場でそれを書いただけです。
しかし、私はこれをPythonなどのより高レベルでパフォーマンスの高い言語で行います: https://stackoverflow.com/questions/3033952/python-thread-pool-similar-to-the-multiprocessing-pool
タスクが単に乱数を生成することである場合:
Perl -e 'for($t=0;$t<1000000;$t++) { print int(Rand()*1000),"\n" }'
あなたのタスクが本当に何か他のものであるなら、あなたはGNU Parallel:
parallel ./random :::: <(seq 1000000) > output
GNU Parallelは、次の方法で簡単にインストールできます。
wget http://git.savannah.gnu.org/cgit/parallel.git/plain/src/parallel
chmod 755 parallel
詳細については、紹介ビデオをご覧ください: http://pi.dk/1