锁的分类总结

article/2025/8/19 1:36:03

锁的分类是从不同角度去看的。同一个锁也可以同时属于多种类型。
在这里插入图片描述

一、乐观锁与悲观锁

1. 互斥同步锁的劣势

  • 阻塞和唤醒会带来性能的劣势
    • 用户态和核心态切换
    • 上下文切换
    • 检查是否有被阻塞线程需要被唤醒
    • 等等
  • 可能出现永久阻塞的问题:持有锁的线程永久阻塞了,比如遇到无限循环、死锁等活跃性问题,那么等待该线程释放锁的那几个线程将永远不能执行。
  • 优先级反转:如果我们为线程设置了优先级,想让优先级低的线程少运行,优先级高的线程多运行,但是一旦优先级低的线程拿到锁后释放得很慢,或者不释放, 就会导致优先级虽然很高,但实际执行起来很低的情况,导致优先级错乱

2. 悲观锁

每次悲观锁为了确保结果的正确性会在每次修改数据时把数据锁住,让别人无法访问该数据,这样就可以确保数据内容的万无一失。
在这里插入图片描述

3. 乐观锁

乐观锁认为自己在处理操作的时候,不会有其他线程来干扰,所以并不会锁住被操作对象。在更新的时候,去对比在我修改期间数据有没有被他人改变过,如果没有改变过,就说明只有自己操作过,那就正常去修改数据,如果被别人修改过,则不对数据进行修改了,选择放弃、报错重试等策略。
乐观锁的实现一般都是利用CAS算法。
在这里插入图片描述

4. 典型例子

4.1 Git

Git 就是乐观锁的典型例子,当我们往远端仓库 push 的时候,git 会检查远端仓库的版本是不是领先于我们现在的版本,如果远程仓库的版本号和本地的不一样,就表示有其他人修改了远端代码了,我们的这次提交就失败;如果远端和本地版本号一致,我们就可以顺利提交版本到远端仓库

4.2 数据库

select for update 就是悲观锁

每次获取商品时,对该商品加排他锁。也就是在用户A获取获取 id=1 的商品信息时对该行记录加锁,期间其他用户阻塞等待访问该记录。悲观锁适合写入频繁的场景。

begin;
select * from table where id = 1 for update;
update set num = num - 1 where id = 1;
commit;

update goods set stock = stock - 1 where id = 1;

用version控制数据库就是乐观锁

添加一个字段 lock_ version
先查询这个更新语句的 version:

select * from goods where id = 1;

然后

begin;
update goods set num = 2, version = version + 1 where version = 1 and id = 1;
commit;

如果 version 被更新了等于 2,不一样就会更新出错,这就是乐观锁的原理。

5. 开销对比

悲观锁的原始开销要高于乐观锁,但是特点是一劳永逸,临界区持锁时间就算越来越长,也不会对互斥锁的开销造成影响。
相反,虽然乐观锁一开始的开销比悲观锁小,但是如果自旋时间很长或者不停重试,那么消耗的资源也会越来越多。

6. 各自的适用场景

悲观锁:适合并发写入多的情况,适用于临界区持锁时间比较长的情况,悲观锁可以避免大量的无用自旋等消耗。
典型情况:

  1. 临界区有I0操作。
  2. 临界区代码复杂或者循环量大。
  3. 临界区竞争非常激烈

乐观锁:适合并发写入少,大部分是读取的场景,不加锁的能让读取性能大幅提高。

二、可重入锁与非可重入锁

1. 什么是可重入?

可重入就是说某个线程已经获得某个锁,可以再次获取该锁。

2. 可重入的好处

  • 避免死锁
  • 提升了封装性

三、公平锁与非公平锁

1. 什么是公平与非公平

公平指的是按照线程请求的顺序,来分配锁;非公平指的是,不完全按照请求的顺序,在一定情况下,可以插队。
注意:非公平也同样不提倡“插队”行为,这里的非公平,指的是“在合适的时机”插队,而不是盲目插队。

2. 为什么要有非公平锁

提高效率,避免唤醒带来的空档期。
假设有A、B、C三个线程,此时A持有这把锁,B就要去等待休息。等A执行完以后释放锁, B就需要被唤醒然后占有这把锁,但是C突然来请求这把锁,C是本身处于唤醒状态,可以立刻执行的,C就很有可能在B被唤醒的过程中就可以占有并使用完释放这把锁了,这就形成了一个“双赢”的局面,是可以带来吞吐量的提升的。

3. 公平锁

在线程 1 执行 unlock(释放锁之后,由于此时线程 2 的等待时间最久,所以线程 2 先得到执行,然后是线程 3 和线程 4。

4. 非公平锁

如果在线程 1 释放锁的时候,线程 5 恰好去获取这把锁。
由于此时并没有线程持有这把锁(线程 2 还没来得及获取到,因为获取需要时间)
线程 5 可以插队,直接拿到这把锁。

5. 公平锁与非公平锁的优缺点

优势劣势
公平锁各线程公平平等,每个线程在等待一段时间后,总有执行的机会更慢、吞吐量更小
非公平锁更快、吞吐量更大有可能产生线程饥饿,也就是某些线程在长时间内始终得不到执行

四、共享锁与排他锁

排他锁,又称为独占锁、独享锁。获取锁之后其他线程不能读或者写,只能由该线程读取或修改数据。

共享锁,又称为读锁,获得共享锁之后,可以查看但无法修改和删除数据,其他线程此时也可以获取到共享锁,也可以查看但无法修改和删除数据

1. 读写锁的规则

  • 多个线程只申请读锁,都可以申请到
  • 如果有一个线程已经占用了读锁,则此时其他线程如果要申请写锁,则申请写锁的线程会一直等待释放读锁。
  • 如果有一个线程已经占用了写锁,则此时其他线程如果申请写锁或者读锁,则申请的线程会一直等待释放写锁。

一句话总结:要么是一个或多个线程同时有读锁,要么是一个线程有写锁,但是两者不会同时出现(要么多读,要多一写)

2. 读锁插队策略

公平情况下: 不允许插队。

非公平的情况下:
假设线程 2 和线程 4 正在同时读取,线程 3 想要写入,拿不到锁,于是进入等待队列,线程 5 不在队列里,现在过来想要读取…
在这里插入图片描述
策略1:

读可以插队,线程5获取读锁。
优点缺点
效率高会造成饥饿

如果有大量的读线程进来,则可能读锁长时间不能释放,线程3长期得不到执行,产生饥饿。

策略2:

读不能插队,线程5进入等待队列。
优点缺点
效率偏低避免了饥饿

因为读锁可以同时被多个线程获取,所以插队能力非常强,要对读锁进行限制,最后策略如下:

  • 写锁可以正常插队
  • 读锁仅在等待队列头部不是写锁的时候可以插队

3. 锁的升级和降级

为什么需要升降级?

比如一个任务,一开始是写操作,然后是读操作, 这样一直占有读锁就会导致资源浪费,但是又不想释放锁重新去排队。这样我们就可以将写锁降级成读锁。

降级操作流程:
在这里插入图片描述
升级的操作流程:
在这里插入图片描述
读锁升级要求其他线程都释放读锁。如果两个线程同时升级还会导致死锁。
结论:读写锁降级容易,升级难。

五、自旋锁和阻塞锁

  • 阻塞或唤醒一个线程需要操作系统切换 CPU 状态来完成,这种状态转换需要耗费处理器时间。
  • 如果同步代码块中的内容过于简单,状态转换消耗的时间有可能比用户代码执行的时间还要长。
  • 在许多场景中,同步资源的锁定时间很短,为了这一小段时间去切换线程,线程挂起和恢复现场的花费可能会让系统得不偿失。
  • 如果物理机器有多个处理器,能够让两个或以上的线程同时并行执行,我们就可以让后面那个请求锁的线程不放弃 CPU 的执行时间,看看持有锁的线程是否很快就会释放锁。
  • 而为了让当前线程“稍等一下”,我们需让当前线程进行自旋,如果在自旋完成后前面锁定同步资源的线程已经释放了锁,那么当前线程就可以不必阻塞而是直接获取同步资源,从而避免切换线程的开销。这就是自旋锁
  • 阻塞锁和自旋锁相反,阻塞锁如果遇到没拿到锁的情况,会直接把线程阻塞,直到被唤醒。

1. 自旋锁的缺点

  • 如果锁被占用的时间很长,那么自旋的线程只会白浪费处理器资源。
  • 在自旋的过程中,一直消耗 cpu,所 以虽然自旋锁的起始开销低于悲观锁,但是随着自旋时间的增长,开销也是线性增长的。

2. 自旋锁的应用场景

自旋锁一般用于多核的服务器,在并发度不是特别高的情况下,比阻塞锁的效率高。

另外,自旋锁适用于临界区比较短小的情况,否则如果临界区很大(线程一旦拿到锁,很久以后才会释放),那也是不合适的。

六、可中断锁

如果某一线程 A 正在执行锁中的代码,另一线程 B 正在等待获取该锁,可能由于等待时间过长,线程不想等待了,想先处理其他事情,我们可以中断它,这种就是可中断锁。


http://chatgpt.dhexx.cn/article/VEsHXCqw.shtml

相关文章

锁的介绍和分类(轻量级锁 重量级锁 偏向锁 自旋锁 互斥锁)

目录 公平锁 非公平锁 非公平锁 公平锁 可重入锁 不可重入锁 可重入锁(递归锁) 不可重入锁 轻量级锁 重量级锁 偏向锁 重量级锁 自旋锁(循环上锁) 轻量级锁 轻量级锁的释放 偏向锁 自旋锁和互斥锁 自旋锁 互斥锁 为何要使用自旋锁 自旋…

最全锁种类

你可能听说过很多锁,也看到过很多文章讲解锁,这篇我在这里将对锁的不同分类进行描述锁的设计 互斥锁–共享锁 互斥锁:顾名思义,就是互斥的,意思就是当前同步代码块只能被一个线程访问,sync、reentrantlock、…

锁的类型有哪些

锁的类型有哪些 基于锁的属性分类:共享锁、排他锁。 基于锁的粒度分类:行级锁(INNODB)、表级锁(INNODB、MYISAM)、页级锁(BDB引擎 )、记录锁、间隙锁、临键锁。 基于锁的状态分类:意向共享锁、意向排它锁 共享锁(Share Lock) 共享锁又称读锁&…

Kettle使用教程之Job使用

1、Kettle的Job使用十分简单,这里也只是演示比较简单的操作,创建Job 2、点击转换,然后点击浏览,选择转换对象 3、执行按钮,运行该转换 4、如果需要长期的进行定时转换,可以在Job中的start控件进行配置 转载…

Kettle使用教程之数据同步

Kettle使用教程之数据同步 数据模型原型如下: 1、表输入,针对最新的数据输入的表 2、目标表,需要更新的表 3、两个表都需要进行排序操作 4、合并,根据id进行合并 5、数据同步(包括更新、插入、删除) 6、点击运行,就可…

ETL开发工具KETTLE使用教程

Kettle的建立数据库连接、使用kettle进行简单的全量对比插入更新:kettle会自动对比用户设置的对比字段,若目标表不存在该字段,则新插入该条记录。若存在,则更新。 Kettle简介:Kettle是一款国外开源的ETL工具&#xff0…

ETL工具Kettle使用教程

Kettle使用教程之数据同步 数据同步标识字段 标志字段的值有4种,分别是: “Identical” : 关键字段在新旧数据源中都存在,且域值相同 “changed” : 关键字段在新旧数据源中都存在,但域值不同 “new” : 旧数据源中没有找到该…

Kettle使用教程(一)—— 在MacOS系统中安装 Kettle

Kettle使用教程(一)—— 在MacOS系统中安装 Kettle 一、环境准备二、下载并启动Kettle二、初始化资源库 一、环境准备 Kettle 9.2JDK 1.8 (安装指引)Mysql(安装指引) 二、下载并启动Kettle 首先到官网下…

Kettle使用教程(问题)

关于kettle的介绍此文不做介绍 笔者电脑环境 winoraclejdk1.8kettle7.1 1. 考虑到在在官网下载速度比较慢,在这里可以使用国内的镜像 国内镜像 2. 配置java环境 (1) kettle需要以来java环境,因为没有安装java环境的朋友请移步配置java环境&#xff…

R-P-Faster R-CNN day65 读论文:高分辨率遥感影像综合地理空间目标检测框架

An Efficient and Robust Integrated Geospatial Object Detection Framework for High Spatial Resolution Remote Sensing Imagery 1. Introduction3. Overview of the Proposed R-P-Faster R-CNN Framework3.1. 有效集成区域建议网络与目标检测Faster R-CNN框架3.1.2. RPN与…

多特征融合的高分辨率遥感图像海陆分离——刘思彤

论文阅读笔记 摘要 为解决目前大多数海陆分离方法仅利用单一特征对图像进行处理,从而导致误分割或存在大量孤立区域,造成后续处理工作难度大或无法开展的问题,提出一种联合灰度、梯度和纹理等多特征的海陆分离方法。针对不同的陆地类型选用…

从实现的技术手段细数:高分辨率遥感影像+人工智能的现在和未来

【转自】http://baijiahao.baidu.com/s?id1601901487917871613&wfrspider&forpc 人工智能不可阻挡地向各行业渗透。这一现象,恰巧撞上了“商业遥感卫星发射潮”。这似乎预示了某种潜流。此刻,从事卫星遥感影像解译和大数据提取的专业人士、科研…

高分辨率光学遥感影像舰船目标检测与识别算法研究(尹莹莹)

论文阅读笔记 摘要 本文主要研究海陆背景下的光学遥感图像舰船目标检测与识别技术,重点研究了海陆分离、舰船目标疑似区域检测技术与疑似区域目标识别技术。 海陆分离: 采用了OTSU与形态学相结合的方法实现海路区域初步划分;再以孤立区域内…

基于高分辨率影像的潍坊大棚遥感提取

1 背景 朋友,当你坐在经过潍坊的火车上的时候,是否被窗外的风景震惊过?那一望无际的大棚,像一片海洋,又像一片草原,连接天际,一眼望不到边。在卫星地图上,白茫茫一片,蔚为…

如何浏览与下载全球免费的地图高分辨率(亚米级)的遥感影像?

目录 一.引言 二、高分辨率的地图数据源简介 1.Google Earth影像 2.Esri World Image 3.天地图 4.必应地图 5.高德地图 三、浏览与下载该地图源 1.Google Earth影像浏览与下载​ 2.Esri World Image的浏览与下载 3.天地图瓦片地址浏览与下载 4.必应地图浏览与下载 …

学习笔记-基于全局和局部对比自监督学习的高分辨率遥感图像语义分割-day2

高分辨率遥感图像语义分割-day2 摘要一、引言二、方法2.1 对比学习2.2 全局风格与局部匹配对比学习网络(GLCNet)2.2.1 全局风格对比学习模块:2.2.2局部匹配对比学习: 三、实验和结果A. 数据说明B. 实验设置1 基线:2 评…

基于全局和局部对比自监督学习的高分辨率遥感图像语义分割day3 - 网络结构

基于全局和局部对比自监督学习的高分辨率遥感图像语义分割day3 - 网络结构 前言自监督学习部分语义分割细调部分总结 前言 想要学习一个网络,最重要的就是网络结构和损失函数,一个讲了网络是怎么学,一个讲了网络将会学成什么样(个…

paddlepaddle打比赛之高分辨率遥感影像建筑物变化检测

★★★ 本文源自AlStudio社区精品项目,【点击此处】查看更多精品内容 >>> 1 赛事背景 城市是人类生活、生产的主要场所,在社会经济活动中处于重要位置。经济发展、人口增长和城市化进程的加快导致了城市地区的急剧变化,准确及时地识…

论文笔记(一)NFANET:一种新的高分辨率遥感影像弱监督水体提取方法

NFANet: A Novel Method for Weakly Supervised Water Extraction from High-Resolution Remote Sensing Imagery NFANET:一种新的高分辨率遥感影像弱监督水体提取方法 作者:Ming Lu,Leyuan Fang,Muxing Li,Bob Zhang,Yi Zhang,Pedram Ghamisi 期刊&…

论文学习笔记:高分辨率遥感影像解译中的机器学习范式

来源:National Remote Sensing Bulletin 遥感学报 作者:周培诚、程塨、姚西文、韩军伟 1. 西北工业大学 深圳研究院 , 深圳 518057; 2. 西北工业大学 自动化学院 , 西安 710072 传统的高分辨率遥感影像解译通常采用人工目视解译方式,费…