日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 人文社科 > 生活经验 >内容正文

生活经验

Linux多线程的同步------读写锁

發(fā)布時間:2023/11/27 生活经验 35 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Linux多线程的同步------读写锁 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

前面介紹過Linux多線程同步的另外兩個方法------互斥鎖和信號量

Linux多線程的同步-----信號量和互斥鎖_神廚小福貴!的博客-CSDN博客

下面來看一下讀寫鎖:

? ? ? ? 讀寫鎖和互斥鎖都帶有一個鎖,那么他們有什么區(qū)別呢?

讀寫鎖互斥鎖
多個讀操作可以同時進行一次只有一個線程擁有互斥鎖,其他線程只有等待
寫操作之間必須互斥
讀寫操作之間也是互斥的,且寫操作的應(yīng)優(yōu)先于讀操作(寫操作執(zhí)行的時候,其他函數(shù)都在阻塞)

上面說到了讀寫鎖和互斥鎖的區(qū)別,相信大家對讀寫鎖已經(jīng)有了一定的理解,下面來看讀寫鎖所用到的函數(shù)以及頭文件:
頭文件:#include <pthread.h>?

讀寫鎖初始化函數(shù):

int pthread_rwlock_init(pthread_rwlock_t *rwlock, pthread_rwlockattr_t *attr);?

第一個參數(shù)是讀寫鎖指針,第二個參數(shù)是讀寫鎖的屬性的指針(一般置為NULL)----下面附上官方手冊

?讀鎖:int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock);?

寫鎖:int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock);?

解鎖:int pthread_rwlock_unlock(pthread_rwlock_t *rwlock);?

銷毀鎖:int pthread_rwlock_destroy(pthread_rwlock_t *rwlock);?

函數(shù)里面的參數(shù)都是所創(chuàng)建的讀寫鎖的指針

下面來看一個代碼示例:下面代碼是沒有加讀寫鎖🔓的代碼

#include <stdio.h>
#include <stdlib.h> 
#include <unistd.h>
#include <string.h>
#include <pthread.h>pthread_rwlock_t rwlock;//讀寫鎖的創(chuàng)建void * read_fun1(void * arg)   //讀子線程的函數(shù)
{while(1){printf("read1 start \n");sleep(1);printf("read2 end \n");}
} 
void * read_fun2(void * arg)
{while(1){printf("read2 start \n");sleep(1);printf("read2 end \n");}
}void * write_fun(void * arg)
{while(1){printf("write start \n");sleep(1);printf("write end  \n");}
}int main()
{pthread_rwlock_init(&rwlock,NULL);pthread_t idr1,idr2; //創(chuàng)建兩個讀的線程pthread_t idw;  //創(chuàng)建一個寫的線程pthread_create(&idr1,NULL,read_fun1,NULL);pthread_create(&idr2,NULL,read_fun2,NULL);pthread_create(&idw,NULL,write_fun,NULL);pthread_join(idr1,NULL);pthread_join(idr2,NULL);pthread_join(idw,NULL);pthread_rwlock_destroy(&rwlock);exit(0);
}
~     

上面代碼沒有加讀寫鎖,我們來運行結(jié)果:

?運行結(jié)果可看出,在讀操作進行的同時,寫操作也在進行著,那么我們再來看一下加了讀寫鎖之后的運行結(jié)果

來看加了讀寫鎖之后的代碼:

#include <stdio.h>
#include <stdlib.h> 
#include <unistd.h>
#include <string.h>
#include <pthread.h>pthread_rwlock_t rwlock;//讀寫鎖的創(chuàng)建void * read_fun1(void * arg)   //讀子線程的函數(shù)
{while(1){pthread_rwlock_rdlock(&rwlock);   //對讀操作枷鎖printf("read1 start \n");sleep(1);printf("read2 end \n");pthread_rwlock_unlock(&rwlock);   //讀完進行解鎖}
} 
void * read_fun2(void * arg)
{while(1){pthread_rwlock_rdlock(&rwlock);   //對讀操作枷鎖printf("read2 start \n");sleep(1);printf("read2 end \n");pthread_rwlock_unlock(&rwlock);   //讀完進行解鎖}
}void * write_fun(void * arg)
{while(1){pthread_rwlock_wrlock(&rwlock);   //對寫操作枷鎖printf("write start \n");sleep(1);printf("write end  \n");pthread_rwlock_unlock(&rwlock);   //寫完進行解鎖}
}int main()
{pthread_rwlock_init(&rwlock,NULL);pthread_t idr1,idr2; //創(chuàng)建兩個讀的線程pthread_t idw;  //創(chuàng)建一個寫的線程pthread_create(&idr1,NULL,read_fun1,NULL);pthread_create(&idr2,NULL,read_fun2,NULL);pthread_create(&idw,NULL,write_fun,NULL);pthread_join(idr1,NULL);pthread_join(idr2,NULL);pthread_join(idw,NULL);pthread_rwlock_destroy(&rwlock);exit(0);
}
~     

加了鎖之后再來運行? ?看結(jié)果:

?看了結(jié)果發(fā)現(xiàn),誒,怎么還是不對啊,怎么沒有寫操作呢?

在我上面的代碼中,是讀操作的線程創(chuàng)建函數(shù)先于寫操作的線程創(chuàng)建函數(shù),然后剛開始就是讀拿鎖,又因為讀操作是可以同時拿鎖的,所以兩個讀操作同時拿鎖,中間可能會有間隔 ,但是這個間隔時間之中是另外一個讀操作在拿鎖,所以寫操作就一直拿不到鎖,但是你只要給每次解鎖之后加個睡眠一秒鐘的函數(shù),就會改善這種情況

#include <stdio.h>
#include <stdlib.h> 
#include <unistd.h>
#include <string.h>
#include <pthread.h>pthread_rwlock_t rwlock;//讀寫鎖的創(chuàng)建void * read_fun1(void * arg)   //讀子線程的函數(shù)
{while(1){pthread_rwlock_rdlock(&rwlock);   //對讀操作枷鎖printf("read1 start \n");sleep(1);printf("read2 end \n");pthread_rwlock_unlock(&rwlock);   //讀完進行解鎖sleep(1);}
} 
void * read_fun2(void * arg)
{while(1){pthread_rwlock_rdlock(&rwlock);   //對讀操作枷鎖printf("read2 start \n");sleep(1);printf("read2 end \n");pthread_rwlock_unlock(&rwlock);   //讀完進行解鎖sleep(1);}
}void * write_fun(void * arg)
{while(1){pthread_rwlock_wrlock(&rwlock);   //對寫操作枷鎖printf("write start \n");sleep(1);printf("write end  \n");pthread_rwlock_unlock(&rwlock);   //寫完進行解鎖sleep(1);}
}int main()
{pthread_rwlock_init(&rwlock,NULL);pthread_t idr1,idr2; //創(chuàng)建兩個讀的線程pthread_t idw;  //創(chuàng)建一個寫的線程pthread_create(&idr1,NULL,read_fun1,NULL);pthread_create(&idr2,NULL,read_fun2,NULL);pthread_create(&idw,NULL,write_fun,NULL);pthread_join(idr1,NULL);pthread_join(idr2,NULL);pthread_join(idw,NULL);pthread_rwlock_destroy(&rwlock);exit(0);
}

加上睡眠函數(shù)之后的運行結(jié)果:

?就可以了,這是因為在讀完數(shù)據(jù)之后,間隔那一秒鐘,讀操作空閑不拿鎖的時候,那個寫操作就可以拿到鎖子,但是這玩意說到底的優(yōu)先級是什么,別人做過實驗,結(jié)果是寫操作優(yōu)先:

讀寫鎖的一個奇怪表現(xiàn) - 付哲 - 博客園

總結(jié)

以上是生活随笔為你收集整理的Linux多线程的同步------读写锁的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。