1. 程式人生 > >兩個執行緒併發執行以下程式碼,假設a是全域性變數,那麼以下輸出___哪個是可能的?

兩個執行緒併發執行以下程式碼,假設a是全域性變數,那麼以下輸出___哪個是可能的?

兩個執行緒併發執行以下程式碼,假設a是全域性變數,那麼以下輸出_哪個是可能的?

int a=1;
void foo(){
    ++a;
    printf("%d",a);
}

解析

假設執行緒x和y同時執行,x和y可隨時被搶佔,a的初始值為1

  • A:3, 2
    y先執行++a,a為2;
    y再執行printf,a入棧,在列印到終端之前切換到x
    x執行++a,a為3;
    x執行printf,輸出3;再切換到y
    y執行列印,輸出2

  • B:2 3
    x先執行++a,a為2;
    x再執行printf,輸出2;切換到y
    y執行++a,a為3;
    y執行printf,輸出3;

  • C:3 3
    x先執行++a,a為2;切換到y
    y執行++a,a為3;
    y執行printf,輸出3;切換到x
    x執行printf,輸出3

  • D:2 2
    類似C, 執行++a操作但沒有寫回到記憶體

這裡關鍵有兩點:
(1)兩個執行緒可隨時被搶佔
(2)++a和printf不是原子指令,可隨時被打斷;特別注意函式printf,a作為引數壓棧後,a再變化則不會影響輸出(printf實際列印的是壓棧的引數,是值拷貝的棧變數)