1. 程式人生 > >使用訊號量解決兩個執行緒同步問題

使用訊號量解決兩個執行緒同步問題

1.同步問題

   我們知道多道程式設計理念的提出,使得執行緒(程序)和執行緒(程序)之間可以併發執行,但是有一些特殊的情況,請看下面的例子:
 (https://img-blog.csdn.net/20170126160159642?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvcXFfMzM2NTA5Nzg=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast)
這就引發了同步問題。

2.解決思路

我們採用訊號量的方式解決該同步問題,即當執行緒B執行之前一直等待執行緒A發出的訊號,一旦接收到執行緒A的訊號,執行緒B掛入就緒佇列準備執行,否則執行緒B一直掛在對應訊號量的等待佇列。

3.程式碼模擬

我們建立兩個執行緒A和B,建立後使其掛起。然後設定訊號量value初始值為0。先Resume B並在其之前設定等待命令,再Resume A並在其之後設定發出訊號命令:

#include "stdafx.h"
#include"stdio.h"
#include "stdlib.h"
#include "windows.h"




void init(){
    int i;
    for(i=0;i<3;i++){
        lock[i]=0;
        number[i]=0;
    }
}



void wait(int
*value,HANDLE w){ (*value)--; if((*value)<0){ SuspendThread(w); } } void signal(int *value,HANDLE w){ (*value)++; if((*value)<=0){ ResumeThread(w); } } DWORD WINAPI AThread(LPVOID lpParameter){ printf("執行緒A正在執行\n"); return 0; } DWORD WINAPI BThread(LPVOID lpParameter){ printf("執行緒B正在執行\n"
); return 0; } int main(){ HANDLE A,B; int S=0; //設定訊號量初始值 init(); B=CreateThread(NULL,NULL,BThread,0,CREATE_SUSPENDED,NULL); A=CreateThread(NULL,NULL,AThread,0,CREATE_SUSPENDED,NULL); wait(&S,B); ResumeThread(B); ResumeThread(A); signal(&S,B); system("pause"); return 0; }
這樣即使cpu先排程Thread B,B也會因為未收到A的訊號,從而掛起。