当前位置: 首页 > article >正文

Linux IPC:读写锁汇总整理

读写锁(Readers-Writers Locks)是一种同步机制,用于允许多个线程同时读取共享资源,但只允许一个线程写入。这种锁的设计目的是为了提高并发性能,尤其是在读操作远比写操作频繁的情况下。下面详细介绍读写锁的概念、用途、API以及示例代码。

a9729d6d7e9e4f63b1622c53d1772f69.jpeg

概述

读写锁的特点如下:

  • 读共享:允许多个线程同时进行读操作。
  • 写独占:一次只能有一个线程进行写操作,且在此期间不允许任何读操作。
  • 写优先:在某些实现中,如果有线程正在等待写锁,那么即使有多个线程持有读锁,也会让等待的写锁线程优先获得锁。
  • 公平性:某些实现会考虑锁请求的先后顺序,以确保公平性。

API

读写锁的主要 API 如下:

  • pthread_rwlock_init():

    • int pthread_rwlock_init(pthread_rwlock_t *rwlock, const pthread_rwlockattr_t *attr): 初始化读写锁。
    • 参数rwlock是指向读写锁变量的指针,attr是属性指针,可以为NULL
  • pthread_rwlock_rdlock():

    • int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock): 获取读锁。
    • 参数rwlock是指向读写锁变量的指针。
  • pthread_rwlock_wrlock():

    • int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock): 获取写锁。
    • 参数rwlock是指向读写锁变量的指针。
  • pthread_rwlock_tryrdlock():

    • int pthread_rwlock_tryrdlock(pthread_rwlock_t *rwlock): 尝试获取读锁,如果锁已经被占用则立即返回。
    • 参数rwlock是指向读写锁变量的指针。
  • pthread_rwlock_trywrlock():

    • int pthread_rwlock_trywrlock(pthread_rwlock_t *rwlock): 尝试获取写锁,如果锁已经被占用则立即返回。
    • 参数rwlock是指向读写锁变量的指针。
  • pthread_rwlock_unlock():

    • int pthread_rwlock_unlock(pthread_rwlock_t *rwlock): 释放读写锁。
    • 参数rwlock是指向读写锁变量的指针。
  • pthread_rwlock_destroy():

    • int pthread_rwlock_destroy(pthread_rwlock_t *rwlock): 销毁读写锁。
    • 参数rwlock是指向读写锁变量的指针。

示例代码

下面是一个简单的示例,展示了如何使用读写锁来同步多个线程的操作:

1#include <pthread.h>
2#include <stdio.h>
3#include <stdlib.h>
4#include <unistd.h>
5
6// 定义读写锁
7pthread_rwlock_t rwlock = PTHREAD_RWLOCK_INITIALIZER;
8int data = 0;
9
10// 读取线程
11void *reader(void *arg) {
12    while (1) {
13        pthread_rwlock_rdlock(&rwlock);  // 获取读锁
14
15        printf("Reader: data=%d\n", data);
16
17        pthread_rwlock_unlock(&rwlock);  // 释放读锁
18
19        sleep(1);  // 休眠一秒
20    }
21}
22
23// 写入线程
24void *writer(void *arg) {
25    while (1) {
26        pthread_rwlock_wrlock(&rwlock);  // 获取写锁
27
28        data++;  // 修改数据
29        printf("Writer: updated data to %d\n", data);
30
31        pthread_rwlock_unlock(&rwlock);  // 释放写锁
32
33        sleep(1);  // 休眠一秒
34    }
35}
36
37int main() {
38    pthread_t reader_tid, writer_tid;
39
40    // 创建读取线程
41    if (pthread_create(&reader_tid, NULL, reader, NULL) != 0) {
42        perror("pthread_create");
43        exit(EXIT_FAILURE);
44    }
45
46    // 创建写入线程
47    if (pthread_create(&writer_tid, NULL, writer, NULL) != 0) {
48        perror("pthread_create");
49        exit(EXIT_FAILURE);
50    }
51
52    // 等待线程结束
53    pthread_join(reader_tid, NULL);
54    pthread_join(writer_tid, NULL);
55
56    return 0;
57}

注意事项

  • 初始化和销毁:确保在使用读写锁之前正确初始化它,并在不再需要时销毁它。
  • 锁的获取和释放:在获取锁后,确保在适当的时候释放锁,以避免死锁或资源泄漏。
  • 尝试获取锁:使用pthread_rwlock_tryrdlock()pthread_rwlock_trywrlock()可以避免无限期等待,从而增加程序的健壮性。
  • 线程取消:在使用读写锁时,确保处理线程取消的情况,避免资源泄漏。

读写锁在多线程编程中非常有用,特别是在读操作远比写操作频繁的场景中。理解和熟练掌握这些概念对于编写高效、可靠的多线程应用程序至关重要。

 


http://www.kler.cn/a/448660.html

相关文章:

  • Ajax中的axios
  • macos 隐藏、加密磁盘、文件
  • ROS1入门教程3:自定义消息
  • 如何调大unity软件的字体
  • clickhouse优化记录
  • WPF 使用LibVLCSharp.WPF实现视频播放、停止、暂停功能
  • linux 合并uboot dtb kernel rootfs 文件制作nor flash 烧录镜像
  • 通过移除 -march=native 解决 Ubuntu 20.04 程序运行“段错误 (核心已转储)”问题的详解
  • TIDB的备份与恢复、上传OSS
  • 制作自己的Manjaro Linux Live DVD 光盘镜像
  • WebRTC服务质量(06)- 重传机制(03) NACK找到真正的丢包
  • Linux之压缩解压相关命令
  • 网上球鞋竞拍系统|Java|SSM|VUE| 前后端分离
  • MVCC了解
  • 2024 高级爬虫笔记(四)协程、selenium
  • 11爬虫:使用requests和selenium分别抓取4399网页游戏名称
  • LeetCode 35. 搜索插入位置 (C++实现)
  • 12.18 web后端开发——数据库
  • 【代码随想录】刷题记录(61)-二叉搜索树中的众数
  • 【Java入门指南 Day12:Java集合框架】
  • PostgreSQL和Postgis安装
  • 正反向代理 Nginx简单使用
  • 麒麟操作系统服务架构保姆级教程(三)ssh远程连接
  • 【从零开始的LeetCode-算法】3285. 找到稳定山的下标
  • LeetCode:1387. 将整数按权重排序(记忆化搜索 Java)
  • 【漏洞复现】CVE-2023-29944 Expression Injection