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

[JAVAee]锁策略

目录

乐观锁与悲观锁

乐观锁

乐观锁的冲突检测

悲观锁

读锁与写锁

重量级锁与轻量级锁 

重量级锁

轻量级锁

自旋锁

公平锁与非公平锁

可重入锁与不可重入锁


乐观锁与悲观锁

乐观锁

在乐观锁中,假设数据并不会发生冲突,在正式提交数据时会对数据进行冲突检测,如果发生了冲突则会返回错误信息,将决定权交给用户

乐观锁的冲突检测

冲突检测是乐观锁的一个重要功能.

实现这个功能的方式主要是:引入一个版本号,每次线程中的工作内存进行操作后,版本号会相应的+1,只有在提交数据工作内存中的版本号大于主存中的版本号才能提交成功.

示例:

在乐观锁下两个线程分别进行+1操作

首先线程1先被调度,将n进行+1操作后版本号也+1.

线程1中的数据要拷贝到主存中,首先要看两者的版本号.线程1中的版本号大于主存中的版本号,可以写入数据.

 此时,线程2也进行+1操作,但线程2中的工作内存n还没有更新.

当线程2想要写入的时候,会发现自己的版本号没有大于主存中的版本号.

写入失败,主存中的数据就不会更新.

悲观锁

总是假设为最坏的情况,每次去拿数据的时候都会认为别人去修改.所以每次去拿数据的时候都会上锁,这样别人再想拿数据的时候就会阻塞.

对于synchronized来说,初始会使用"乐观锁",发现竞争比较激烈的时候才会自动转换到"悲观锁"

读锁与写锁

在多线程的环境下,数据的读取线程之间是不会互斥的,但读取线程与写入线程之间会互斥.

如果两种情景下,都使用同一把锁.就会产生极大的性能损耗.

为了解决这种情况,就有了读锁与写锁(readers-writer lock)

对于读操作与写操作

  • 线程之间的读操作,并不会有线程安全的问题,可以之间并发读取.
  • 线程之间的写操作,就会产生线程安全的问题.
  • 线程之间的读操作与写操作,会产生线程安全的问题.

 读写锁就可以把这些情况都区分开,降低性能的消耗.

在java标准库中,提供了ReentrantReadWriteLock类,其中实现了读锁写.

ReentrantReadWriteLock reentrantReadWriteLock = new ReentrantReadWriteLock();ReentrantReadWriteLock.ReadLock readLock = reentrantReadWriteLock.readLock();
readLock.lock();
readLock.unlock();ReentrantReadWriteLock.WriteLock writeLock = reentrantReadWriteLock.writeLock();
writeLock.lock();
writeLock.unlock();

其中:(互斥就是线程会进入阻塞状态)

  1. 读锁与读锁之间不互斥
  2. 写锁与写锁之间互斥
  3. 读锁与写锁之间互斥

读写锁适用于频繁读,但不频繁写的场景下.

重量级锁与轻量级锁 

锁的核心特性为:"原子性".

这种特性的来源,能追溯到CPU这种硬件提供的.

  • CPU 提供了 "原子操作指令".
  • 操作系统基于 CPU 的原子指令, 实现了 mutex 互斥锁.
  • JVM 基于操作系统提供的互斥锁, 实现了 synchronized 和 ReentrantLock 等关键字和类.

重量级锁

加锁机制依赖操作系统(内核态)提供mutex.

就会发生大量的内核态与用户态之间的转换即线程的调度

轻量级锁

加锁机制尽量不依赖于操作系统的mutex,而是在用户态中使用代码实现.如果无法实现,再去调用mutex.

可以减少内核态与用户态之间的转换

 synchronized初始为轻量级锁,在竞争激烈的时候才转换为重量级锁

自旋锁

线程在抢锁失败后会进入阻塞状态(放弃CPU,暂时停止运行).需要经过较久的时间才会被重新调度.

通常情况下,抢夺的锁很快就会被释放出来.就没必要进入阻塞(放弃CPU).

自旋锁就可以解决这种情况.

自旋锁在竞争锁失败后,会立即尝试获取锁,循环直到成功获取到锁.一旦锁被释放,很快就能够获取到.

自旋锁虽然能在锁被释放的第一时间获取到锁,但如果锁被占用的时间较长就会持续的消耗CPU的资源.

公平锁与非公平锁

  • 公平锁:遵守先来后到的顺序,先尝试获取锁的线程首先能占用到
  • 非公平锁:不遵守先来后到的顺序,随机调度

在操作系统中,锁的调度都是随机的.如果不加以任何限制,那么其就是一个非公平锁.

而实现公平锁,需要一个额外的数据结构来存储线程尝试获取锁的顺序.

synchronized是一个非公平锁

可重入锁与不可重入锁

可重入锁的字面意思是“可以重新进入的锁”,即允许同一个线程多次获取同一把锁.加锁后仍然可以进行递归操作重新获取锁而不会阻塞自己的锁就为可重入锁.(因为这个原因可重入锁也叫做递归锁)

synchronized是可重入锁
 

相关文章:

[JAVAee]锁策略

目录 乐观锁与悲观锁 乐观锁 乐观锁的冲突检测 悲观锁 读锁与写锁 重量级锁与轻量级锁 重量级锁 轻量级锁 自旋锁 公平锁与非公平锁 可重入锁与不可重入锁 乐观锁与悲观锁 乐观锁 在乐观锁中,假设数据并不会发生冲突,在正式提交数据时会对数据进行冲突检测,如果发…...

uni-app-使用tkiTree组件实现树形结构选择

前言 在实际开发中我们经常遇见树结构-比如楼层区域-组织架构-部门岗位-系统类型等情况 往往需要把这个树结构当成条件来查询数据,在PC端可以使用Tree,table,Treeselect等组件展示 在uni-app的内置组件中似乎没有提供这样组件来展示&#x…...

SQL-每日一题【1179. 重新格式化部门表】

题目 部门表 Department: 编写一个 SQL 查询来重新格式化表,使得新的表中有一个部门 id 列和一些对应 每个月 的收入(revenue)列。 查询结果格式如下面的示例所示: 解题思路 1.题目要求我们重新格式化表,…...

GO语言语法结构

GO语言结构 包声明引入包函数变量语句 && 表达式注释 package main import "fmt" func main() {fmt.Println("Hello,World!") } 如这段代码块根据上面的语法结构进行逐行解释 第一行的 package main 是定义一个包名,必须在源文件…...

C++学习——模板

目录 🍉一:什么是模板 🍎二:普通模板的定义 🍍三:类模板的定义 🍌四:模板的实例化 🍇1.当普通模板定义存在可修改返回值产生的分歧 🍈2:类模板实例…...

二叉树的遍历(先序遍历,中序遍历,后序遍历)递归与非递归算法

目录 一、先序遍历题目链接1.递归2.非递归 二、中序遍历题目链接1.递归2.非递归 三、后序遍历题目链接1.递归2.非递归 一、先序遍历 先序遍历:先遍历一颗树的根节点,后遍历左子树,最后遍历右子树 先序遍历序列: 1 -> 2 -> 4…...

【LeetCode】516. 最长回文子序列

文章目录 1. 思路讲解1.1 创建dp表1.2 状态转移方程1.3 不需考虑边界问题 2. 整体代码 1. 思路讲解 1.1 创建dp表 此题采用动态规划的方法,创建一个二维dp表,dp[i][j]表示s[i, j]中最大回文子序列的长度。且我们人为规定 i 是一定小于等于 j 的。 1.2…...

Java 集合框架

Java 集合框架提供了一组接口和类,以实现各种数据结构和算法。 集合框架满足以下几个要求。 该框架必须是高性能的。基本集合(动态数组,链表,树,哈希表)的实现也必须是高效的。 该框架允许不同类型的集合…...

遇到多人协作,我们该用git如何应对?(版本二)

一、多人协作二 1.1多人协作 一般情况下,如果有多需求需要多人同时进行开发,是不会在一个分支上进行多人开发,而是一个需求或一个功能点就要创建一个feature 分支。 现在同时有两个需求需要你和你的小伙伴进行开发,那么你们俩便…...

Flutter iOS 集成使用 fluter boost

在 Flutter项目中集成完 flutter boost,并且已经使用了 flutter boost进行了路由管理,这时如果需要和iOS混合开发,这时就要到 原生端进行集成。 注意:之前建的项目必须是 Flutter module项目,并且原生项目和flutter m…...

node.js相关的npm包的集合

一、实用功能 1. qs 一个简单易用的字符串解析和格式化库 2.rxjs RxJS是一组模块化的库,用于使用 JavaScript 中的可观察集合和组合来组合异步和基于事件的程序。 3. mitt 微型 200b 功能事件发射器/发布订阅. 4.Underscore.js Underscore.js是一个用于 JavaScript…...

Android Ble蓝牙App(二)连接与发现服务

Ble蓝牙App(二)连接与发现服务 前言正文一、GATT回调二、连接和断连三、连接状态回调四、发现服务五、服务适配器六、显示服务七、源码 前言 在上一篇中我们进行扫描设备的处理,本文中进行连接和发现服务的数据处理,运行效果图如下…...

Android 自定义按钮(可滑动、点击)

按钮图片素材 https://download.csdn.net/download/Lan_Se_Tian_Ma/88151085 px 和 dp 转换工具类(Java) // px 和 dp 转换工具类 public class DensityUtil {/*** 根据手机的分辨率从 dip 的单位 转成为 px(像素)*/public static int dip2px(Conte…...

mac录屏怎么打开?很简单,让我来教你!

mac电脑作为一款广受欢迎的电脑系统,提供了多种方式来满足用户录屏的需求。无论您是要录制教学视频、制作演示文稿,还是记录游戏精彩瞬间,mac电脑都能帮助您实现这些目标。本文将为您介绍两种mac录屏的方法。通过本文的指导,您将能…...

Stable Diffusion AI绘画学习指南【插件安装设置】

插件安装的方式 可用列表方式安装,点开Extensions 选项卡,找到如下图,找到Available选项卡,点load from加载可用插件,在可用插件列表中找到要装的插件按install 按扭按装,安装完后(Apply and restart UI)应…...

APP开发中的性能优化:提升用户满意度的关键

APP开发中的性能优化是需要持续进行的,它不仅能够让用户体验到 APP的使用感受,还能在一定程度上提升用户的满意度,从而提升 APP的粘性和转化率。不过在实际开发中,很多 APP开发公司会存在性能优化上的问题,这就需要了解…...

Golang 切片 常用方法

文章目录 移除指定位置的元素查找元素的位置查找最大最小的元素去重随机打乱排序二维排序sort.Sort 排序 下面的方法省略一些校验,如数组越界等,且都采用泛型(要求go版本 > 1.18) 移除指定位置的元素 package mainimport ("fmt" )func Del…...

【Linux后端服务器开发】poll/epoll多路转接IO服务器

目录 一、poll原理 二、poll实现多路转接IO服务器 三、epoll函数接口 四、epoll的工作原理 五、epoll实现多路转接IO服务器 一、poll原理 poll函数接口 #include <poll.h> int poll(struct pollfd *fds, nfds_t nfds, int timeout);// pollfd结构 struct pollfd …...

【设计模式——学习笔记】23种设计模式——命令模式Command(原理讲解+应用场景介绍+案例介绍+Java代码实现)

文章目录 案例引入介绍基础介绍登场角色 案例实现案例一实现 案例二介绍实现拓展 命令模式在JdbcTemplate源码中的应用总结文章说明 案例引入 有一套智能家电&#xff0c;其中有照明灯、风扇、冰箱、洗衣机&#xff0c;这些智能家电来自不同的厂家&#xff0c;我们不想针对每一…...

Rust中的高吞吐量流处理

本篇文章主要介绍了Rust中流处理的概念、方法和优化。作者不仅介绍了流处理的基本概念以及Rust中常用的流处理库&#xff0c;还使用这些库实现了一个流处理程序。 最后&#xff0c;作者介绍了如何通过测量空闲和阻塞时间来优化流处理程序的性能&#xff0c;并将这些内容同步至…...

高频面试之3Zookeeper

高频面试之3Zookeeper 文章目录 高频面试之3Zookeeper3.1 常用命令3.2 选举机制3.3 Zookeeper符合法则中哪两个&#xff1f;3.4 Zookeeper脑裂3.5 Zookeeper用来干嘛了 3.1 常用命令 ls、get、create、delete、deleteall3.2 选举机制 半数机制&#xff08;过半机制&#xff0…...

江苏艾立泰跨国资源接力:废料变黄金的绿色供应链革命

在华东塑料包装行业面临限塑令深度调整的背景下&#xff0c;江苏艾立泰以一场跨国资源接力的创新实践&#xff0c;重新定义了绿色供应链的边界。 跨国回收网络&#xff1a;废料变黄金的全球棋局 艾立泰在欧洲、东南亚建立再生塑料回收点&#xff0c;将海外废弃包装箱通过标准…...

Qt Http Server模块功能及架构

Qt Http Server 是 Qt 6.0 中引入的一个新模块&#xff0c;它提供了一个轻量级的 HTTP 服务器实现&#xff0c;主要用于构建基于 HTTP 的应用程序和服务。 功能介绍&#xff1a; 主要功能 HTTP服务器功能&#xff1a; 支持 HTTP/1.1 协议 简单的请求/响应处理模型 支持 GET…...

ip子接口配置及删除

配置永久生效的子接口&#xff0c;2个IP 都可以登录你这一台服务器。重启不失效。 永久的 [应用] vi /etc/sysconfig/network-scripts/ifcfg-eth0修改文件内内容 TYPE"Ethernet" BOOTPROTO"none" NAME"eth0" DEVICE"eth0" ONBOOT&q…...

Mobile ALOHA全身模仿学习

一、题目 Mobile ALOHA&#xff1a;通过低成本全身远程操作学习双手移动操作 传统模仿学习&#xff08;Imitation Learning&#xff09;缺点&#xff1a;聚焦与桌面操作&#xff0c;缺乏通用任务所需的移动性和灵活性 本论文优点&#xff1a;&#xff08;1&#xff09;在ALOHA…...

【Go语言基础【12】】指针:声明、取地址、解引用

文章目录 零、概述&#xff1a;指针 vs. 引用&#xff08;类比其他语言&#xff09;一、指针基础概念二、指针声明与初始化三、指针操作符1. &&#xff1a;取地址&#xff08;拿到内存地址&#xff09;2. *&#xff1a;解引用&#xff08;拿到值&#xff09; 四、空指针&am…...

【网络安全】开源系统getshell漏洞挖掘

审计过程&#xff1a; 在入口文件admin/index.php中&#xff1a; 用户可以通过m,c,a等参数控制加载的文件和方法&#xff0c;在app/system/entrance.php中存在重点代码&#xff1a; 当M_TYPE system并且M_MODULE include时&#xff0c;会设置常量PATH_OWN_FILE为PATH_APP.M_T…...

FFmpeg avformat_open_input函数分析

函数内部的总体流程如下&#xff1a; avformat_open_input 精简后的代码如下&#xff1a; int avformat_open_input(AVFormatContext **ps, const char *filename,ff_const59 AVInputFormat *fmt, AVDictionary **options) {AVFormatContext *s *ps;int i, ret 0;AVDictio…...

五子棋测试用例

一.项目背景 1.1 项目简介 传统棋类文化的推广 五子棋是一种古老的棋类游戏&#xff0c;有着深厚的文化底蕴。通过将五子棋制作成网页游戏&#xff0c;可以让更多的人了解和接触到这一传统棋类文化。无论是国内还是国外的玩家&#xff0c;都可以通过网页五子棋感受到东方棋类…...

Qt的学习(一)

1.什么是Qt Qt特指用来进行桌面应用开发&#xff08;电脑上写的程序&#xff09;涉及到的一套技术Qt无法开发网页前端&#xff0c;也不能开发移动应用。 客户端开发的重要任务&#xff1a;编写和用户交互的界面。一般来说和用户交互的界面&#xff0c;有两种典型风格&…...