開發使用多執行緒過程中, 不可避免的會出現多個執行緒同時操作同一塊共享資源, 當操作全部為讀時, 不會出現未知結果, 一旦當某個執行緒操作中有寫操作時, 就會出現資料不同步的事件.
而出現資料混亂的原因:
以上三點, 前兩點不能被改變. 欲提高效率, 傳遞資料, 資源必須共享. 只要資源共享, 就一定會出現執行緒間資源競爭, 只要存在競爭關係, 資料就會出現混亂.
所以只能從第三點著手, 使多個執行緒在訪問共享資源的時候, 出現互斥.
執行緒同步:
指在一定的時間裡只允許某乙個程序訪問某個資源,而在此時間內,不允許其它執行緒對該資源進行操作.
執行緒的同步機制:
前兩章已經介紹完了互斥量(互斥鎖),讀寫鎖,和條件變數, 本章來介紹重點的訊號量
訊號量又稱進化版的互斥鎖----> 互斥鎖只能同時有乙個執行緒進行訪問,而訊號量可以同時有n個執行緒同時進行.
由於互斥鎖的粒度比較大,如果我們希望在多個執行緒間結某一物件的部分資料進行共享,使用互斥鎖是沒有辦法實現的,只能將整個資料物件鎖住.這樣雖然達到了多執行緒操作共享資料時保證資料正確性的目的,卻無形之中導致執行緒的併發性下降.執行緒從並行執行,變成了串形執行.與直接使用單程序無異.
訊號量,是相對折中的一種處理方式,既能保證同步,資料不混亂,又能提高執行緒併發性.
首先來看看條件變數所常用的函式:
sem_init(sem_t* sem, int pshared, unsigned int value);
作用:初始化乙個訊號量
引數1: sem訊號量
引數2: pshared 取0用於執行緒間,取非0(一般為1)用於程序間
引數3: value 指定訊號量的初值
sem_destroy(sem_t* sem);
作用:銷毀乙個訊號量
引數: 指定乙個已經初始化的sem訊號量
sem_wait(sem_t* sem);
作用:給訊號量加鎖(對訊號量的值作--操作,如果此時訊號量的值已為0 阻塞等待)
引數:指定乙個已經初始的sem訊號量
sem_post(sem_t* sem);
作用:給訊號量解鎖(對訊號量的值作++操作)
引數:指定乙個已經初始的sem訊號量
sem_trywait(sem_t* sem);
作用:嘗試對訊號量加鎖(如果此時訊號量的值已為0,立即返回.不會阻塞)
引數:指定乙個已經初始的sem訊號量
sem_timedwait(sem_t* sem, const struct timespec* abs_timeout);
作用:限定時間內對訊號量嘗試加鎖(時間為當前絕對時間)
引數1: 指定乙個已經初始化的sem訊號量
引數2: 指定絕對時間 結構體如下struct timespec;
案例:乙個執行緒讀使用者輸入,另乙個執行緒列印"hello world".如果使用者無輸入,則每隔5秒向螢幕列印乙個"hello world";如果使用者有輸入,則立即列印"hello world"到螢幕[思考]
12
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
#include
#include
#include
#include
#include
#include
sem_t sem;
//全域性訊號量
void
* thread_handler(
void
* agrs);
//初始化當前時間
while
(1)
}
int
main(
int
argc,
char
* agrv);
while
(1)
//等待執行緒退出
pthread_join(tid, null);
return
0;
}
Linux 執行緒同步 訊號量
linux 執行緒同步訊號量 訊號量用於多執行緒多工同步,乙個執行緒完成了某乙個動作後就通過訊號量告訴其他執行緒再進行某些動作,其他執行緒在等待某乙個執行緒時會阻塞。init sem t sem sem init sem,0,0 函式原型如下 int sem init sem t sem,intps...
Linux 執行緒同步之訊號量同步
linux中兩種基本的同步方法是訊號量和互斥量。這兩種方法很相似,而且它們可以相互通過對方來實現。下面介紹用訊號量進行同步。訊號量概念由荷蘭科學家dijkstra首先提出。訊號量是乙個特殊型別的變數,它可以被增加或者減少。但對其的關鍵訪問被保證是原子操作,即使在乙個多執行緒程式中也是如此。訊號量有兩...
Linux 執行緒同步之訊號量同步
linux中兩種基本的同步方法是訊號量和互斥量。這兩種方法很相似,而且它們可以相互通過對方來實現。下面介紹用訊號量進行同步。訊號量概念由荷蘭科學家dijkstra首先提出。訊號量是乙個特殊型別的變數,它可以被增加或者減少。但對其的關鍵訪問被保證是原子操作,即使在乙個多執行緒程式中也是如此。訊號量有兩...