【线程】互斥锁
一、互斥鎖
1. 函數(shù)原型
pthread_mutex_init(pthread_mutex_t *restrict mutex, const pthread_mutexattr_t *restrict attr); pthread_mutex_destroy(pthread_mutex_t *mutex);分析:
- pthread_mutex_t 類(lèi)型,其本質(zhì)是一個(gè)結(jié)構(gòu)體,為簡(jiǎn)化理解,應(yīng)用時(shí)可忽略其實(shí)現(xiàn)細(xì)節(jié),簡(jiǎn)單當(dāng)成整數(shù)看待。
- pthread_mutex_t??mutex:變量mutex只有兩種取值0、1;
函數(shù)一參數(shù)1:傳出參數(shù),調(diào)用時(shí)應(yīng)傳&mutex
- restrict關(guān)鍵字:只用于限制指針,告訴編譯器,所有修改該指針指向內(nèi)存中內(nèi)容的操作,只能通過(guò)本指針完成。不能通過(guò)除本指針以外的其他變量或指針修改。
函數(shù)一參數(shù)2:互斥屬性。是一個(gè)傳入?yún)?shù),通常傳NULL,選用默認(rèn)屬性(線程間共享).
- 靜態(tài)初始化:如果互斥鎖mutex是靜態(tài)分配的(定義在全局,或加了static關(guān)鍵字修飾),可以直接使用宏進(jìn)行初始化。pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
- 動(dòng)態(tài)初始化:局部變量應(yīng)采用動(dòng)態(tài)初始化, pthread_mutex_init(&mutex, NULL);
?
?
2. 函數(shù)原型:
pthread_mutex_lock(pthread_mutex_t *mutex); pthread_mutex_unlock(pthread_mutex_t *mutex);分析:
- 函數(shù)1:沒(méi)有被上鎖,當(dāng)前線程會(huì)將這把鎖鎖上;被鎖上了,當(dāng)前線程阻塞,鎖被打開(kāi)之后,線程解除阻塞(加鎖。可理解為將mutex--(或-1))。
- 函數(shù)2:同時(shí)將阻塞在該鎖上的所有線程全部喚醒解鎖(可理解為將mtex++(或+1)).
?
二、代碼清單
1. 測(cè)試代碼
#include <stdio.h> #include <string.h> #include <pthread.h> #include <stdlib.h> #include <unistd.h>void *tfn(void *arg) {srand(time(NULL));while(1) {printf("hello ");sleep(rand() % 3); //模擬長(zhǎng)時(shí)間操作共享資源,導(dǎo)致cpu易主,產(chǎn)生與時(shí)間有關(guān)的錯(cuò)誤printf("word\n");sleep(rand() % 3);}return NULL; }int main() {pthread_t tid;srand(time(NULL));pthread_create(&tid, NULL, tfn, NULL);while(1) {printf("HELLO ");sleep(rand() % 3);printf("WORLD\n");sleep(rand() % 3);}return 0; }輸出結(jié)果?
?
?
2. 測(cè)試代碼?
#include <stdio.h> #include <string.h> #include <pthread.h> #include <stdlib.h> #include <unistd.h>void *tfn(void *arg) {srand(time(NULL));while(1) {printf("hello ");sleep(rand() % 3); //模擬長(zhǎng)時(shí)間操作共享資源,導(dǎo)致cpu易主,產(chǎn)生與時(shí)間有關(guān)的錯(cuò)誤printf("word\n");sleep(rand() % 3);}return NULL; }int main() {pthread_t tid;srand(time(NULL));pthread_create(&tid, NULL, tfn, NULL);while(1) {printf("HELLO ");sleep(rand() % 3);printf("WORLD\n");sleep(rand() % 3);}return 0; }輸出結(jié)果
?
#include<pthread.h> #include<stdlib.h> #include<unistd.h>pthread_mutex_t mutex;void* tfn(void* arg) {srand(time(NULL));while (1) {pthread_mutex_lock(&mutex);printf("hello ");sleep(rand() % 3); //模擬長(zhǎng)時(shí)間共享資源,導(dǎo)致cpu易主。產(chǎn)生于時(shí)間有關(guān)的錯(cuò)誤 printf("word\n");pthread_mutex_unlock(&mutex);sleep(rand() % 3);}return NULL; }int main() {pthread_t tid;srand(time(NULL));pthread_mutex_init(&mutex, NULL);pthread_create(&tid, NULL, tfn, NULL); //mutex == 1while (1) {pthread_mutex_lock(&mutex);printf("HELLO ");sleep(rand() % 3);printf("WORLD\n");pthread_mutex_unlock(&mutex);sleep(rand() % 3);}pthread_mutex_destroy(&mutex);return 0; }?
#include<stdlib.h> #include<unistd.h> #include<pthread.h> #include<errno.h> #include<stdio.h>pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER; pthread_mutex_t *mp;void add(void) {int i = 10;i = i + 1;i = i + 2;i = i + 3;printf("sum is %d\n", i); }void thread1(void) {{pthread_mutex_lock(mp);add();pthread_mutex_unlock(mp);sleep(1);} } void thread2(void) {{pthread_mutex_lock(mp);add();pthread_mutex_unlock(mp);sleep(2);} }int main(void) {pthread_t id1, id2;int ret;mp = (pthread_mutex_t*)malloc(sizeof(pthread_mutex_t));pthread_mutex_init(mp, NULL);ret = pthread_create(&id1, NULL, (void*)thread1, NULL);if(ret < 0){perror("pthread_create id1");exit(1);}ret = pthread_create(&id2, NULL, (void*)thread2, NULL);if(ret <0){perror("pthread_create id2");exit(1);}pthread_join(id1, NULL); pthread_join(id2, NULL); pthread_mutex_destroy(mp);free(mp);return 0; }?
創(chuàng)作挑戰(zhàn)賽新人創(chuàng)作獎(jiǎng)勵(lì)來(lái)咯,堅(jiān)持創(chuàng)作打卡瓜分現(xiàn)金大獎(jiǎng)總結(jié)