簡単な質問:大規模なプロジェクトをより速くコンパイルするためにg ++がそれ自体の複数のインスタンスを生成できるようにするコンパイラフラグとは何ですか(たとえば、マルチコアCPUで一度に4つのソースファイル)。
make -j
ほとんどの場合、賢明な使用はある程度の改善につながります。
簡単な質問:大規模なプロジェクトをより速くコンパイルするためにg ++がそれ自体の複数のインスタンスを生成できるようにするコンパイラフラグとは何ですか(たとえば、マルチコアCPUで一度に4つのソースファイル)。
make -j
ほとんどの場合、賢明な使用はある程度の改善につながります。
回答:
これはmakeで行うことができます-gnu makeでは-jフラグです(これはユニプロセッサーマシンでも役立ちます)。
たとえば、makeから4つの並列ジョブが必要な場合:
make -j 4
パイプでgccを実行することもできます
gcc -pipe
これにより、コンパイル段階がパイプライン化され、コアをビジー状態に保つのにも役立ちます。
利用可能な追加のマシンもある場合は、distccをチェックアウトすることもできます。これにより、ファームコンパイルもそれらにコンパイルされます。
-j
議論
そのようなフラグはなく、各ツールに1つの機能だけを実行させ、それを適切に実行させるというUnixの哲学に反するものがあります。コンパイラー・プロセスの生成は、概念的にはビルド・システムの仕事です。あなたがおそらく探しているのは、GNU makeの-j(jobs)フラグです。
make -j4
または、pmakeまたは同様の並列makeシステムを使用できます。
makeを使用している場合は、を発行し-j
ます。からman make
:
-j [jobs], --jobs[=jobs] Specifies the number of jobs (commands) to run simultaneously. If there is more than one -j option, the last one is effective. If the -j option is given without an argument, make will not limit the number of jobs that can run simultaneously.
そして最も注目すべきは、スクリプトを作成したり、使用可能なコアの数を特定したりする場合(環境によって異なり、多くの環境で実行すると、状況が大きく変化する可能性があります)、ユビキタスPython関数を使用できますcpu_count()
。
https://docs.python.org/3/library/multiprocessing.html#multiprocessing.cpu_count
このような:
make -j $(python3 -c 'import multiprocessing as mp; print(int(mp.cpu_count() * 1.5))')
1.5
上記のコメントでなぜ私がユーザーartless-noiseを引用するのかと尋ねている場合:
1.5の数値は、指摘されたI / Oバウンドの問題が原因です。経験則です。ジョブの約1/3がI / Oを待機するため、残りのジョブは使用可能なコアを使用します。コアよりも大きい数の方が優れており、2倍にもなる可能性があります。
make -j`nproc`
とnproc
GNUのCoreutilsに。
make -j $(( $(nproc) + 1 ))
私がいる場所にスペースを入れてください)。
nproc
です。たとえば、manylinux1
コンテナー内で使用できないシステムでは、yum update
/の実行を回避することで追加の時間を節約できますyum install
。
distccは、現在のマシンだけでなく、distccがインストールされているファーム内の他のマシンにもコンパイルを配布するために使用できます。
GNUパラレル
私は合成コンパイルのベンチマークを作成していて、Makefileを作成する気にならなかったので、次を使用しました。
sudo apt-get install parallel
ls | grep -E '\.c$' | parallel -t --will-cite "gcc -c -o '{.}.o' '{}'"
説明:
{.}
入力引数を取り、その拡張子を削除します-t
実行中のコマンドを出力して、進捗状況を知らせます--will-cite
ソフトウェアを使用して結果を公開する場合、ソフトウェアを引用する要求を削除します...parallel
私はタイムスタンプチェックを自分で行うことさえできるほど便利です:
ls | grep -E '\.c$' | parallel -t --will-cite "\
if ! [ -f '{.}.o' ] || [ '{}' -nt '{.}.o' ]; then
gcc -c -o '{.}.o' '{}'
fi
"
xargs -P
ジョブを並行して実行することもできますが、拡張機能を操作したり、複数のコマンドを実行したりするのは少し不便です。xargsを使用した複数のコマンドの呼び出し
並列リンクが尋ねられました:gccはリンク時に複数のコアを使用できますか?
TODO:コンパイルを行列の乗算に削減できることをどこかで読んだので、大きなファイルの単一ファイルのコンパイルを高速化することも可能かもしれません。しかし、私は今、参照を見つけることができません。
Ubuntu 18.10でテスト済み。