4

C++11 スレッド化ライブラリを使用してマルチスレッド化 (および一般的なマルチスレッド化) を始めたばかりで、短い短いコードを書きました。

 #include <iostream>
 #include <thread>

int x = 5; //variable to be effected by race 

    //This function will be called from a thread
    void call_from_thread1() {
    for (int i = 0; i < 5; i++) { 
           x++;
          std::cout << "In Thread 1 :" << x << std::endl;
        }
    }    

    int main() {
        //Launch a thread
        std::thread t1(call_from_thread1);

       for (int j = 0; j < 5; j++) {
            x--;
            std::cout << "In Thread 0 :" << x << std::endl;
        }

        //Join the thread with the main thread
        t1.join();

    std::cout << x << std::endl;
    return 0;
    }

2 つのスレッド間の競合のため、このプログラムを実行するたびに (またはほぼ毎回) 異なる結果が得られると予想していました。ただし、出力は常に : です0。つまり、2 つのスレッドが順番に実行されたかのように実行されます。同じ結果が得られるのはなぜですか? 2 つのスレッド間の競合をシミュレートまたは強制する方法はありますか?

4

2 に答える 2

8

サンプルサイズはかなり小さく、継続的な stdout フラッシュで自己停止します。つまり、より大きなハンマーが必要です。

実際の競合状態の動作を見たい場合は、次のことを考慮してください。意図的にアトミック カウンターと非アトミック カウンターを追加し、両方をサンプルのスレッドに送信しました。コードの後に​​いくつかのテスト実行結果が掲載されています。

#include <iostream>
#include <atomic>
#include <thread>
#include <vector>

void racer(std::atomic_int& cnt, int& val)
{
    for (int i=0;i<1000000; ++i)
    {
        ++val;
        ++cnt;
    }
}

int main(int argc, char *argv[])
{
    unsigned int N = std::thread::hardware_concurrency();
    std::atomic_int cnt = ATOMIC_VAR_INIT(0);
    int val = 0;

    std::vector<std::thread> thrds;
    std::generate_n(std::back_inserter(thrds), N,
        [&cnt,&val](){ return std::thread(racer, std::ref(cnt), std::ref(val));});

    std::for_each(thrds.begin(), thrds.end(),
        [](std::thread& thrd){ thrd.join();});

    std::cout << "cnt = " << cnt << std::endl;
    std::cout << "val = " << val << std::endl;
    return 0;
}

上記のコードからいくつかのサンプルを実行します。

cnt = 4000000
val = 1871016

cnt = 4000000
val = 1914659

cnt = 4000000
val = 2197354

アトミックカウンターが正確であることに注意してください(私はハイパースレッディングを備えたデュオコアi7 macbook airラップトップで実行しているため、4xスレッド、したがって400万です)。非アトミックカウンターについても同じことは言えません。

于 2013-10-10T03:14:55.757 に答える