实际场景
大多数情况下,线程只是读取共享变量的值,并不修改;只有少数情况下,线程才真正修改共享变量的值
"读" & "写" 场景下的临界区保护
多个线程同时读取一个共享变量时,并不存在冲突 (无须保护)
只有在线程写共享变量时,才需要对其进行保护
问题:互斥量可用于多线程 "读" & "写" 共享变量的场景吗?
互斥量是一种普适的解决方案,其缺点是效率不够出色
因此,针对多线程 "读" & "写" 场景需要更具针对性的解决方案
针对 "读" & "写" 的特殊锁
读锁:允许多个线程同时访问共享变量 (读取值)
写锁:只允许一个线程单独访问共享变量 (改变值)
问题:
什么时候用 "读锁"?什么时候用 "写锁"?
Linux 中的读写锁 API 函数
读写锁示例程序
读写锁应用要点
保护临界区时,必须清楚当前需要使用 "读锁" 还是 "写锁"
无论是 "读锁" 还是 "写锁",解锁都是调用 pthread_rwlock_unlock()
- 如果所有线程都使用 "读锁",则临界区失去保护
- 如果所有线程都使用 "写锁",则读写锁退化为互斥量
问题
如果两个线程 "同时" 拿到了 "读锁" 和 "写锁",问:哪个线程先进入临界区执行?
读优先 or 写优先
读优先:拿到 "读锁" 的线程优先进入临界区
写优先:拿到 "写锁" 的线程优先进入临界区
读写优先 API 函数
读写锁深度剖析
读写锁在实现上比互斥量复杂,单纯的 "上锁" 和 "解锁" 操作读写锁相对互斥量低效
例:读写场景,如果临界区比较短小,且并发量不大,读写锁并不比互斥量高效
即便只有一个读写锁可也能导致死锁: