2016-08-15 4 views
3

私は並列に実行したいですか?(は同時に実行しません。)私は並列性が新しく、いくつか質問があります。私がこれをしたい理由は、のパフォーマンスが本当に重要だからです。私にとってはです。私は4コアのWindowsマシンで作業していますが、Visual Studio Community 2015でC++を使用しています。異なるコア(並列性)でそれぞれ4つのスレッドを実行するにはどうすればいいですか?

1.スレッドを自分のスケジュールに合わせて、それぞれ別のコアで実行するようにしてください。私はそれを行うOSスケジューラを残していますか?私はそれが別のコアで各スレッドを実行するように強制すると私の意見では、私は速いと思う。どうやってやるの?

は、これは私がこれまでにしようとしているものです:

#include <thread> 
void t1(){//do something} 
void t2(){//do something} 
void t3(){//do something} 
void t4(){//do something} 

int main(){ 
    std::thread thread1(t1); 
    std::thread thread2(t2); 
    std::thread thread3(t3); 
    std::thread thread4(t4); 

    t1.join(); 
    t2.join(); 
    t3.join(); 
    t4.join(); 
} 

私はそれが終了するまでそのスレッド()ブロックに参加する知っています。しかし、スレッドを並行して実行するかどうかはわかりません。私のコードはスレッドを並行して、または並列に実行していますか?例を教えてもらったり、チュートリアルをお勧めしますか?可能であれば、外部ライブラリを使用せずに。

おかげ

EDIT:

同時実行 2つのタスクが同時に実行されているときに、本質的です。これは、一方が短期間「一時停止」され、他方が作業中であることを意味する可能性があります。

並列性は、少なくとも2つのプロセス/タスクが特定の瞬間に積極的に実行されている必要があります。

+0

"同時にまたは並行して" < - これらの単語は同じことを意味します。何を聞いていますか? – Blorgbeard

+2

実行するコアスレッドを選択することはできません。これはオペレーティングシステムによって行われます。 –

+0

@Blorgbeard並行性と並列性の編集と検索を参照してください。 – mata

答えて

4

何かをスケジュールする必要はありません。使用可能なプロセッサが複数ある場合、スレッドは使用可能なコアで同時に実行されます。

使用可能なプロセッサが4つ以下、たとえば2の場合、スレッドはインターリーブされた方法で実行され、任意の時点で最大2つのスレッドが実行されます。


p.s. 4つの無限ループを作成し、4つの異なるスレッドで実行するだけで簡単に体験できます。 4つのCPUが使用されています。


免責事項:もちろん、「フードの下」、スケジューリングはOSによって自動的に行われています。したがって、OSに組み込まれているスケジューラの品質によって、並行性が決まります。 C++アプリケーションが実行されるOSに組み込まれているスケジューラの公正さは、C++標準外であるため、保証されません。現実には、特に並列アプリケーションを書くことを学ぶ場合、ほとんどの最新のOSはスレッドのスケジューリングにおいて十分な公平性を提供します。

+0

@rustynは100%確信しています。上に書いたコードでは、私はそれらを同時に実行しています(上の定義は同時に表示されていません)。ありがとう – mata

+0

@ママ - 利用可能なプロセッサが4つある限り、並列で実行されます。 – rustyx

+0

'std :: async(std :: launch :: async、t1());'などを使用します。特にVSで。 http://stackoverflow.com/questions/26730287/c11-thread-vs-async-performance-vs2013http://stackoverflow.com/questions/26730287/c11-thread-vs-async-performance-vs2013 – doug

-1

場合によっては、アプリケーションアフィニティを設定することもできます。基本的に、4cores/8threadsのi7 CPUのようなものをお持ちの場合、スレッドごとではなく、コアごとに1つのスレッドをアフィニティに設定すると、アプリの方が速くなります。

そうするコマンドラインツールがあります:Set affinity with start /AFFINITY command on Windows 7

はまた、親和性は、タスクマネージャで設定することができます:指定されたスレッドの親和性を設定する標準的な方法は、ボンネットのstdの下で、http://www.windowscentral.com/assign-specific-processor-cores-apps-windows-10

+0

"親和性を1コアあたり1つのスレッドに設定すると、アプリはより速くなります"という証明はありますか? – Slava

+0

@Slavaハイパースレッディングとは、共有リソース(キャッシュ、分岐予測子など)を共有することを意味します。良い読書:http://www.agner。org/optimize/blog/read.php?i = 6&v = t –

+0

より簡単で適切な方法は、ハイパースレッディングをまったく無効にすることです。スレッドの親和性は、初心者のためではなく、頻繁に(主にクールファクターによって)悪用され、良いよりも害を及ぼす可能性があります。 – Slava

1

ありません:: threadは、linux/unixesではposixスレッドを使用し、WindowsではWindowsスレッドを使用して実装されています。

auto fn = []() {while (true);}; 
    std::vector<std::thread> at; 
    const int num_of_cores = 8; 
    for (int n = 0; n < num_of_cores; n++) { 
    at.push_back(std::thread(fn)); 
    // for POSIX: use pthread_setaffinity_np 
    BOOL res = SetThreadAffinityMask(at.back().native_handle(), 1u << n); 
    assert(res); 
    } 
    for (auto& t : at) t.join(); 

が、SetThreadAffinityMaskをコメントアウトした後、私はまだ同じ結果、すべてのコアを取得:ソリューションは、私のi7のCPUのすべての8つのコアのフル活用を引き起こしますコード次のウィンドウの下で、たとえば、ネイティブAPIを使用することです完全に利用されているので、Windowsスケジューラはうまく機能します。

システムコアをよりよく制御したい場合は、OpenMP、TBB(スレッドビルディングブロック)、PPLなどのライブラリを調べます。この順番で。

関連する問題