19-你知道哪几种锁?分别有什么特点?

article/2025/3/17 13:03:38

首先会对锁的分类有一个整体的概念,了解锁究竟有哪些分类标准。

锁的 7 大分类

需要首先指出的是,这些多种多样的分类,是评价一个事物的多种标准,比如评价一个城市,标准有人口多少、经济发达与否、城市面积大小等。而一个城市可能同时占据多个标准,以北京而言,人口多,经济发达,同时城市面积还很大。

同理,对于 Java 中的锁而言,一把锁也有可能同时占有多个标准,符合多种分类,比如 ReentrantLock 既是可中断锁,又是可重入锁。

根据分类标准我们把锁分为以下 7 大类别,分别是:

  • 偏向锁/轻量级锁/重量级锁;

  • 可重入锁/非可重入锁;

  • 共享锁/独占锁;

  • 公平锁/非公平锁;

  • 悲观锁/乐观锁;

  • 自旋锁/非自旋锁;

  • 可中断锁/不可中断锁。

  • 以上是常见的分类标准,下面我们来逐一介绍它们的含义。

偏向锁/轻量级锁/重量级锁

第一种分类是偏向锁/轻量级锁/重量级锁,这三种锁特指 synchronized 锁的状态,通过在对象头中的 mark word 来表明锁的状态。

  • 偏向锁

如果自始至终,对于这把锁都不存在竞争,那么其实就没必要上锁,只需要打个标记就行了,这就是偏向锁的思想。一个对象被初始化后,还没有任何线程来获取它的锁时,那么它就是可偏向的,当有第一个线程来访问它并尝试获取锁的时候,它就将这个线程记录下来,以后如果尝试获取锁的线程正是偏向锁的拥有者,就可以直接获得锁,开销很小,性能最好。

  • 轻量级锁

JVM 开发者发现在很多情况下,synchronized 中的代码是被多个线程交替执行的,而不是同时执行的,也就是说并不存在实际的竞争,或者是只有短时间的锁竞争,用 CAS 就可以解决,这种情况下,用完全互斥的重量级锁是没必要的。轻量级锁是指当锁原来是偏向锁的时候,被另一个线程访问,说明存在竞争,那么偏向锁就会升级为轻量级锁,线程会通过自旋的形式尝试获取锁,而不会陷入阻塞。

  • 重量级锁

重量级锁是互斥锁,它是利用操作系统的同步机制实现的,所以开销相对比较大。当多个线程直接有实际竞争,且锁竞争时间长的时候,轻量级锁不能满足需求,锁就会膨胀为重量级锁。重量级锁会让其他申请却拿不到锁的线程进入阻塞状态。
在这里插入图片描述
你可以发现锁升级的路径:无锁→偏向锁→轻量级锁→重量级锁。

综上所述,偏向锁性能最好,可以避免执行 CAS 操作。而轻量级锁利用自旋和 CAS 避免了重量级锁带来的线程阻塞和唤醒,性能中等。重量级锁则会把获取不到锁的线程阻塞,性能最差。

可重入锁/非可重入锁

第 2 个分类是可重入锁和非可重入锁。可重入锁指的是线程当前已经持有这把锁了,能在不释放这把锁的情况下,再次获取这把锁。同理,不可重入锁指的是虽然线程当前持有了这把锁,但是如果想再次获取这把锁,也必须要先释放锁后才能再次尝试获取。

对于可重入锁而言,最典型的就是 ReentrantLock 了,正如它的名字一样,reentrant 的意思就是可重入,它也是 Lock 接口最主要的一个实现类。

共享锁/独占锁

第 3 种分类标准是共享锁和独占锁。共享锁指的是我们同一把锁可以被多个线程同时获得,而独占锁指的就是,这把锁只能同时被一个线程获得。我们的读写锁,就最好地诠释了共享锁和独占锁的理念。读写锁中的读锁,是共享锁,而写锁是独占锁。读锁可以被同时读,可以同时被多个线程持有,而写锁最多只能同时被一个线程持有。

公平锁/非公平锁

第 4 种分类是公平锁和非公平锁。公平锁的公平的含义在于如果线程现在拿不到这把锁,那么线程就都会进入等待,开始排队,在等待队列里等待时间长的线程会优先拿到这把锁,有先来先得的意思。而非公平锁就不那么“完美”了,它会在一定情况下,忽略掉已经在排队的线程,发生插队现象。

悲观锁/乐观锁

第 5 种分类是悲观锁,以及与它对应的乐观锁。悲观锁的概念是在获取资源之前,必须先拿到锁,以便达到“独占”的状态,当前线程在操作资源的时候,其他线程由于不能拿到锁,所以其他线程不能来影响我。而乐观锁恰恰相反,它并不要求在获取资源前拿到锁,也不会锁住资源;相反,乐观锁利用 CAS 理念,在不独占资源的情况下,完成了对资源的修改。

自旋锁/非自旋锁

第 6 种分类是自旋锁与非自旋锁。自旋锁的理念是如果线程现在拿不到锁,并不直接陷入阻塞或者释放 CPU 资源,而是开始利用循环,不停地尝试获取锁,这个循环过程被形象地比喻为“自旋”,就像是线程在“自我旋转”。相反,非自旋锁的理念就是没有自旋的过程,如果拿不到锁就直接放弃,或者进行其他的处理逻辑,例如去排队、陷入阻塞等。

可中断锁/不可中断锁

第 7 种分类是可中断锁和不可中断锁。在 Java 中,synchronized 关键字修饰的锁代表的是不可中断锁,一旦线程申请了锁,就没有回头路了,只能等到拿到锁以后才能进行其他的逻辑处理。而我们的 ReentrantLock 是一种典型的可中断锁,例如使用 lockInterruptibly 方法在获取锁的过程中,突然不想获取了,那么也可以在中断之后去做其他的事情,不需要一直傻等到获取到锁才离开。


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

相关文章

mysql数据库锁有哪几种_Mysql数据库的分布式锁有哪几种?

原标题:Mysql数据库的分布式锁有哪几种? 文章内容 作者:jstu 文章来自:博客 链接:https://blog.csdn.net/lovexiaotaozi/article/details/83819916 你可能喜欢的文章 1Mysql性能优化一:SQL语句性能优化 悲观…

锁的分类和介绍

java中的各种锁详细介绍 转自:https://blog.csdn.net/axiaoboge/article/details/84335452 Java提供了种类丰富的锁,每种锁因其特性的不同,在适当的场景下能够展现出非常高的效率。本文旨在对锁相关源码(本文中的源码来自JDK 8&a…

java线程锁有哪几种_java中常见的几种锁有哪些

公平锁/非公平锁 公平锁是指多个线程按照申请锁的顺序来获取锁。 非公平锁是指多个线程获取锁的顺序,并不是按照申请锁的顺序,有可能后申请的线程比先申请的线程优先获取锁,有可能,会造成优先级反转或者饥饿现象。 独享锁/共享锁 …

常见的各种锁总结

常见的各种锁 一、常见锁简单说明 1、悲观锁 悲观锁认为自己在使用数据的时候一定有别的线程来修改数据,在获取数据的时候先加锁,确保数据的安全性。 锁实现:关键字synchronized、Lock接口的实现 使用场景:写操作比较多&#xff0…

BioGRID 互作数据库

01 — BioGRID BioGRID 是 Biological General Repository for Interactionh Datasets 的缩写(网址为 https://thebiogrid.org),是一个公开的数据库,主要记录、整理包括蛋白、遗传和化学互作的数据,涵盖人类和所有主要…

Fuzzing论文:Reinforcement Learning-based Hierarchical Seed Scheduling for Greybox Fuzzing

Reinforcement Learning-based Hierarchical Seed Scheduling for Greybox Fuzzing 整体内容论文内容多级代码覆盖指标(用于种子聚类)分层种子调度策略实验 论文题目Reinforcement Learning-based Hierarchical Seed Scheduling for Greybox Fuzzing工具…

BIO的理解

前言 bio:b有两说,一为base,jdk中最早抽象出的io体系;一为block,jdk 1.0 中的io体系是阻塞的。所以两说皆有道理,一般我们认为b取block之意 nio:n也有两说,一为new,针对…

BIO初步学习

1.一个服务端一个客户端 具体代码实现 服务端 public class Server {public static void main(String[] args) {try {ServerSocket serverSocket new ServerSocket(9999);Socket socket serverSocket.accept();InputStream inputStream socket.getInputStream();Buffered…

12.BIO详解

Java BIO 就是传统的 java io 编程, 其相关的类和接口在 java.io 中. BIO 编程简单流程 服务器端启动一个 ServerSocket.客户端启动 Socket 对服务器进行通讯, 默认情况下服务器需要对每个客户建立一个县线程与之通讯.客户端发出请求后, 先咨询服务器是否有线程响应, 如果没有…

bioinformatics小技巧

文章目录 1. 软件安装1.1 linux上python2的安装1.2 Mercurial 安装及使用1.3 tRNAscan的安装和使用1.4 Linux上安装miniconda 2.数据下载2.1 linux上通过ftp下载一个文件夹下的全部文件2.2 GEO数据库数据下载 3.操作系统3.1 Windows下将R设置为环境变量。3.2 Linux 下怎样快速查…

brat标注的ann文件,转为BIO序列标注

这个地方真的好少有人写到,踩了好久的坑都不知道怎么解决。 首先,在用brat自带的转换序列标注的文件时,运行程序 1、python2 anntoconll.py ../data/data_new/corpoa.txt 报错: File "anntoconll.py", line 154, in…

BIO学习笔记

视频地址:https://www.bilibili.com/video/BV1gz4y1C7RK?fromsearch&seid15021234423448500976 2. JAVA BIO深入剖析 Java BIO 就是传统的 java io 编程,其相关的类和接口在 java.io。 BIO(blocking I/O) : 同步阻塞,服务器…

BIO实例

使用 BIO 模型编写一个服务器端,监听 6666 端口,当有客户端连接时,就启动一个线程与之通讯。要求使用线程池机制改善,可以连接多个客户端.服务器端可以接收客户端发送的数据(telnet 方式即可)。 图 代码演示: package…

利用 bioconda 管理生物信息软件

利用 bioconda 管理生物信息软件 如需视频讲解,请移步:一只小蛮要 【要知道 bioinfo】利用 bioconda 管理生物信息软件 1 了解 conda,anaconda,miniconda,bioconda 1.1 conda conda是一个软件模块管理工具&#xff…

IMex和IntAct数据库简介

欢迎关注微信公众号《生信修炼手册》! 蛋白质相互作用的数据库非常的多,比如DIP, MINT, IntAct, BioGRID等,不同数据库中的信息存在了大量的冗余,而且在不同数据库之间进行检索也非常的费力,为了减少不同数据库的冗余&#xff0c…

【Bio】基础生物学 - 基因 gene

文章目录 1. DNA 脱氧核糖核酸、RNA 核糖核酸1.1 核苷酸1.2 脱氧核糖核酸1.3 核糖核酸 2. 基因2.1 基因组2.2 染色体2.3 基因与脱氧核苷酸的牵连2.4 基因与DNA的牵连2.5 基因与染色体的牵连 Ref 1. DNA 脱氧核糖核酸、RNA 核糖核酸 1.1 核苷酸 核苷酸 (Nucleotide) \blue{\tex…

Bioedit 使用

1. 下载: 地址一搜就有,软件界面如下 BioEdit Download - Research software utility for creating and editing biological sequences 2. 酶切位点分析 构建过表达质粒、双荧光素酶质粒必用功能。以人的MYOD1基因为例 ,分析酶切位点。 &…

BIO~~

BIO~~ 第一章 Java的I/O演进之路2.1 I/O 模型基本说明2.2 I/O模型Java BIOJava NIOJava AIO 2.3 BIO、NIO、AIO 适用场景分析 第三章 JAVA BIO深入剖析3.1 Java BIO 基本介绍3.2 Java BIO 工作机制3.3 传统的BIO编程实例回顾客户端案例如下服务端案例如下小结 3.4 BIO模式下多发…

python处理数据的一些代码

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 一、如何读取txt文件,将其转化为DataFrame格式二、给DataFrame添加列名三、删除指定行四、读取csv文件,不让第一行成为列名五、读取DataFram…

BioGRID:蛋白质相互作用数据库

欢迎关注微信公众号《生信修炼手册》! BioGRID数据库是一个老牌经典的蛋白质相互作用数据库,在今年9月份刚刚分布了最新版本3.5.165,该版本从66,164篇文献中整理出了1,607,037个蛋白质相互作用,28,093个嵌合体信息以及726,378个转录后修饰PTM…