@Baileはコメントで言及しているように、これはアプリケーション、システム、環境固有のものです。
このように、私は、コアごとに正確に1つのスレッドを言及する強硬なアプローチをとるつもりはありません。 (ハイパースレッディングの場合は2つのスレッド/コア)
経験豊富な共有メモリプログラマとして、最適なスレッド数(4コアマシンの場合)は1から64の範囲で設定できます+。
今私は、この範囲を引き起こす可能性の状況を列挙します:
最適なスレッドコアの<#非常に(このような小さなFFTのような)並列きめの細かいされている特定のタスクで
、スレッディングのオーバーヘッドが主要なパフォーマンス要因です。場合によっては、並列化することはまったく役に立ちません。場合によっては、2つのスレッドでスピードアップしますが、4つのスレッドで後方にスケーリングします。
もう1つの問題は、リソースの競合です。 4つのコア/スレッドに簡単に分割できる高度に並列化可能なタスクがあっても、メモリ帯域幅とキャッシュ効果によってボトルネックになる可能性があります。たいていの場合、2つのスレッドは4つのスレッドと同じくらい速くなることがわかります。
最適スレッド=コアの#
(非常に大きいのFFTの場合、しばしばかのように)これは、最適なケースです。コアごとに1つのスレッド - ここで説明する必要はありません。メモリやI/Oに縛られていない最も恥ずかしがりな並列アプリケーションはここに適合します。
最適なスレッド>それが面白いところコア
の#これは...非常に興味深いです。負荷の不均衡について聞いたことがありますか?過分解と作業盗みはどうですか?
多くの並列化可能なアプリケーションは不規則です。つまり、タスクは同じサイズのサブタスクに分割されません。だから、大きなタスクを4つの不等なサイズに分割してしまうと、それらを4つのスレッドに割り当てて、4つのコアでそれらを実行すると...結果は? 1つのスレッドが他のスレッドよりも10倍多くの処理を行うため、並列パフォーマンスが悪い
ここでの一般的な解決方法は、に多くのサブタスクにタスクをオーバー分解します。それぞれのスレッドを作成することができます(スレッド >>コア)。あるいは、一定数のスレッドでタスクスケジューラを使用することもできます。すべてのタスクが両方に適しているわけではありませんので、4コアマシンで8または16スレッドにタスクを過度に分解するアプローチが最適な結果をもたらします。
スレッドを追加すると負荷分散が向上する可能性がありますが、オーバーヘッドが増えます。だから、典型的にどこかに最適な点があります。私は4つのコアで最高64スレッドを見ました。しかし、言及したように、それは非常にアプリケーション特有です。そして実験する必要があります。
EDIT:
は、コンテキストスイッチのコストは何です...質問に答えるより直接的に答えを拡大?ストアと復元の時間は CPUは異なるコンテキストに登録されますか?
これは環境に非常に依存しており、直接測定するのは多少困難です。
短い答え:非常に高価This might be a good read.
何 CPU内部キャッシュ、パイプラインおよび各種のコード予測の事についてはどうですか?コンテキストを切り替えるたびに、キャッシュにCPUの パイプラインといくつかのコードデコード機能が壊れていると言うことができますか?
短い答え:はいあなたコンテキストが出て切り替えると、あなたはおそらく、すべての予測を、あなたのパイプラインと混乱をフラッシュします。キャッシュと同じです。新しいスレッドは、キャッシュを新しいデータで置き換える可能性があります。
キャッチはありますがスレッドが同じデータを共有するアプリケーションでは、あるスレッドが、別の着信スレッドまたは同じキャッシュを共有する別のコアの別のスレッドのキャッシュを潜在的に「温める」可能性があります。(まれに、これは私のNUMAマシンの前で起こりました - 超高速のスピードアップ:16コアにわたって17.6x!)!
単一のコア上で実行されるスレッドが多いほど、シリアル実行と比較して を一緒に実行できますか?
依存している...ハイパースレッディングを除いて、間違いなくオーバーヘッドがあります。しかし、私は誰かが2番目のスレッドを使ってメインスレッドを先読みした紙を読みました...はい、それは狂っています...
答えは、アプリケーション、システム、およびマシンに大きく依存しています。しかし、それはおそらく4よりも大きいですが、スレッド数が50未満です。 4,6,8,10のスレッドで測定しようとしましたか? –
4スレッド(または8ワイパー/ハイパースレッディング)。少ないデータ部分。より良いキャッシュ特性。 – bestsss