2012-04-13 79 views
0

我在線發現的代碼顯示瞭如何使用redKyle教程中的線程。在'Race Condition'教程中,他基本上展示了兩個線程如何發送到一個函數。該功能的目標是打印'。'。和'#',每個序列一百次。他提供的代碼讓這個工作,他不提供互斥體的代碼。我修改了代碼以包含互斥體,以防止一個線程訪問保存在另一個線程訪問它時打印的最後一個字符的變量。 我得到的代碼工作。大!不過,我一直在改變1到50之間的睡眠值。互斥代碼工作正常。但是,當我將睡眠設置爲0(或只是將其註釋掉)時,互斥鎖不再有效,並且值不再以正確的方式打印(我不再看到200個字符嚴格交替'#'和'。')。爲什麼睡眠功能禁用我的互斥鎖

以下是代碼:

#include "stdafx.h" 

#include <iostream> 
#include <windows.h> 
using namespace std; 

static char lastChar='#'; 

//define a mutex 
HANDLE mutexHandle = NULL; 

//flag to specify if thread has begun 
bool threadStarted = false; 

void threadProc(int *sleepVal, int *threadID) 
{ 

    cout<<"sleepVal: "<<*sleepVal<<endl; 

    for (int i=0; i<100; i++) 
    { 

     char currentChar; 

     threadStarted = true; 

     while(!threadStarted){} 

     //lock mutex 
     WaitForSingleObject(mutexHandle, INFINITE); 

     if (lastChar == '#') 
      currentChar = '.'; 
     else 
      currentChar = '#'; 

     Sleep(*sleepVal); 

     lastChar = currentChar; 

     ReleaseMutex(mutexHandle); 

     threadStarted = false; 


     //  cout<<"\nSleepVal: "<<*sleepVal<<" at: "<<currentChar; 
     cout<<currentChar; 
    }//end for 
}//end threadProc 

int main() 
{ 
    cout<<"Race conditions by redKlyde \n"; 

    int sleepVal1 = 50; 
    int sleepVal2 = 30; 

    //create mutex 
    mutexHandle = CreateMutex(NULL, false, NULL); 

    //create thread1 
    HANDLE threadHandle; 
    threadHandle = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) threadProc, &sleepVal1, 0, NULL); 

    //create thread2 
    HANDLE threadHandle2; 
    threadHandle2 = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) threadProc, &sleepVal2, 0, NULL); 

    WaitForSingleObject(threadHandle, INFINITE); 
    WaitForSingleObject(threadHandle2, INFINITE); 

    cout<<endl<<endl; 

    CloseHandle(mutexHandle); 

    system("pause"); 

    return 0; 

} 

所以我的問題是:爲什麼設置睡眠0無效互斥代碼。

回答

1

請注意您的打印語句不受互斥鎖保護,因此一個線程可以自由打印,而另一個線程可以自由修改。通過不睡覺,您可以讓調度程序根據線程的數量確定打印順序。

有些事情不對:

1)你不應該保留的鎖內睡覺。這幾乎是不正確的。 2)任何你的數據共享的地方,你應該用鎖來守護。這意味着打印語句也應該處於鎖定狀態。

+0

好的很好,thanx聖哈辛托。我把睡眠從鎖中取出,並將打印語句包含在鎖中。很好地工作,並使得更多的意義! – 2012-04-13 19:24:21

1

此外,作爲未來使用互斥的提示,在Windows上,最好的usermode互斥體是SRWLock,接着是CriticalSection。使用基於句柄的同步對象要慢得多。