以下のコードを並列化したい:
for(int c=0; c<n; ++c) {
Work(someArray, c);
}
私はそれをこのようにしました:
#include <thread>
#include <vector>
auto iterationsPerCore = n/numCPU;
std::vector<std::future<void>> futures;
for(auto th = 0; th < numCPU; ++th) {
for(auto n = th * iterationsPerCore; n < (th+1) * iterationsPerCore; ++n) {
auto ftr = std::async( std::launch::deferred | std::launch::async,
[n, iterationsPerCore, someArray]()
{
for(auto m = n; m < n + iterationsPerCore; ++m)
Work(someArray, m);
}
);
futures.push_back(std::move(ftr));
}
for(auto& ftr : futures)
ftr.wait();
}
// rest of iterations: n%iterationsPerCore
for(auto r = numCPU * iterationsPerCore; r < n; ++r)
Work(someArray, r);
問題は、Intel CPUでは50%しか高速に動作しないのに対し、AMDでは300%高速に動作することです。3つのIntelCPU(Nehalem 2core + HT、Sandy Bridge 2core + HT、Ivy Brigde 4core + HT)で実行します。AMDプロセッサはPhenomIIx2で、4コアのロックが解除されています。2コアのIntelプロセッサでは、4つのスレッドで50%高速に実行されます。4コアでは、4スレッドでも50%高速に実行されます。VS2012、Windows7でテストしています。
8スレッドで試してみると、Intelのシリアルループよりも8倍遅くなっています。HTが原因だと思います。
あなたはそれについてどう思いますか?そのような行動の理由は何ですか?たぶんコードが正しくありませんか?