【转】-java多线程读写锁ReadWriteLock

Java多线程中读写锁ReadWriteLock的使用

该博客转载自​**lavimerJava多线程中读写锁ReadWriteLock的使用**

1. 概念

读写锁分为读锁和写锁,多个读锁之间是不需要互斥的(读操作不会改变数据,如果上了锁,反而会影响效率),写锁和写锁之间需要互斥,也就是说,如果只是读数据,就可以多个线程同时读,但是如果你要写数据,就必须互斥,使得同一时刻只有一个线程在操作。

2. 案例

2.1 三线程读数据,三线程写数据
package com.tao.leanrn.thread.lock;import java.util.concurrent.locks.ReadWriteLock;
import java.util.concurrent.locks.ReentrantReadWriteLock;/*** @ClassName ReadWrite* @Descriiption 读写锁* @Author yanjiantao* @Date 2019/8/21 10:42**/
public class ReadWrite {/*** 共享数据*/private int data = 0;/*** 读写锁*/private ReadWriteLock lock = new ReentrantReadWriteLock();public void get() {// 上读锁lock.readLock().lock();try {System.out.println(Thread.currentThread().getName() + "----->读锁开始执行...");Thread.sleep((long)(Math.random() * 10));System.out.println(Thread.currentThread().getName() + "----->读锁得到数据data=" + data);} catch (InterruptedException e) {e.printStackTrace();} finally {// 释放锁lock.readLock().unlock();}}public void set() {// 上写锁lock.writeLock().lock();try {System.out.println(Thread.currentThread().getName() + "----->写锁开始执行...");Thread.sleep((long)(Math.random() * 10));data++;System.out.println(Thread.currentThread().getName() + "----->写锁得到数据data=" + data);} catch (InterruptedException e) {e.printStackTrace();} finally {// 释放写锁lock.writeLock().unlock();}}
}/*** 测试类*/
class Main{public static void main(String[] args) {ReadWrite readWrite = new ReadWrite();// 创建100个读写线程for (int i = 0; i < 100; i++) {new Thread(() -> {readWrite.get();}).start();new Thread(() -> {readWrite.set();}).start();}}}

程序运行结果

1706261828185.png

2.2 模拟Hibernate缓存
public class HibernateCache {/* 定义一个Map来模拟缓存 */private Map<String, Object> cache = new HashMap<String, Object>();/* 创建一个读写锁 */private ReadWriteLock rwLock = new ReentrantReadWriteLock();/*** 模拟Hibernate缓存* @param key* @return*/private Object getData(String key) {/* 上读锁 */rwLock.readLock().lock();/* 定义从缓存中读取的对象 */Object value = null;try {/* 从缓存中读取数据 */value = cache.get(key);if (value == null) {/* 如果缓存中没有数据,我们就把读锁关闭,直接上写锁【让一个线程去数据库中取数据】 */rwLock.readLock().unlock();/* 上写锁 */rwLock.writeLock().lock();try {/* 上了写锁之后再判断一次【我们只让一个线程去数据库中取值即可,当第二个线程过来的时候,发现value不为空了就去缓存中取值】 */if (value == null) {/* 模拟去数据库中取值 */value = "hello";}} finally {/* 写完之后把写锁关闭 */rwLock.writeLock().unlock();}/* 缓存中已经有了数据,我们再把已经 关闭的读锁打开 */rwLock.readLock().lock();}} finally {/* 最后把读锁也关闭 */rwLock.readLock().unlock();}return value;}}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/44080.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【OpenCV】BGR三色通道的提取与合并--超详细解读

在OpenCV中&#xff0c;处理图像时经常需要提取或合并图像的RGB&#xff08;红、绿、蓝&#xff09;三色通道。OpenCV默认使用BGR&#xff08;蓝、绿、红&#xff09;顺序来存储图像的颜色通道&#xff0c;这一点与很多图像处理库&#xff08;如PIL/Pillow&#xff09;不同&…

Android Constant expression required (case R.id.xxx)

gradle更新到8.0后&#xff0c;遇到了这个报错 有两种解决方式&#xff1a; 1、在gradle.properties中添加下面代码 android.nonFinalResIdsfalse 2、使用if-else来判断 int id view.getId(); if (id R.id.setting_iv_back) {} else if (id R.id.setting_tv_clear) {}

大数据面试题之GreenPlum(1)

目录 介绍一下GreenPlum GreenPlum属于哪家公司的产品&#xff0c;简单说下发展历史 GreenPlum如何处理大数据 GreenPlum有哪些优势 GreenPlum的缺点有哪些 如何优化GreenPlum的性能 如何监控和分析GreenPlum的性能指标 Greenplum整体架构信息 说下Master主机与Segment…

Web知识库应用程序LibreKB

什么是 LibreKB &#xff1f; LibreKB 是一款知识库 Web 应用程序。免费、开源、自托管&#xff0c;基于 PHP/MySQL。 官方并没有 Docker 镜像&#xff0c;老苏这次图省事&#xff0c;并没有像往常一样构建一个镜像&#xff0c;而是基于 Docker 搭建了一个 LAMP 环境&#xff0…

判断一个字符串中出现次数最多的字符,统计这个次数?

1、核心算法&#xff1a;利用 charAt() 遍历这个字符串 2、把每个字符都存储给对象&#xff0c;如果对象没有该属性就为1&#xff0c;如果存了就1 3、遍历对象&#xff0c;得到最大值及出现次数和该字符 let str "aozisodsdkksdsd" let obj {} for (let i 0; i &l…

ConditionalOnJndi注解使用介绍、应用场景以及示例代码

概述 ConditionalOnJndi 是 Spring Framework 中的一个条件注解&#xff0c;用于在特定的 JNDI (Java Naming and Directory Interface) 环境条件下决定是否创建一个 bean 或配置一个 bean。JNDI 是 Java EE 规范中定义的一种用于访问命名和目录服务的 API&#xff0c;它允许 …

蹭一个围棋亚军!不要和低维的人说话——早读(逆天打工人爬取热门微信文章解读)

熬夜后需要补什么呢&#xff1f; 引言Python 代码第一篇 洞见 不要和低维的人说话&#xff08;深度好文&#xff09;第二篇 冲冲冲结尾 引言 昨晚真的是熬夜又想不出东西 真的头大 最近下围棋 这个棋感很好呀 我是K级选手 目前是8级 套几个buff 纯自学 为什么决定学围棋呢? 是…

谷粒商城配置中心错误记录

文章目录 一&#xff0c;com.alibaba.nacos.api.exception.NacosException: endpoint is blank1&#xff0c;分析定位2&#xff0c;关于配置文件application和bootstrap的区别与练习加载顺序使用说明 参考文献 一&#xff0c;com.alibaba.nacos.api.exception.NacosException: …

AI工具:软件开发者的革命性助手还是潜在威胁?

近年来&#xff0c;生成式人工智能&#xff08;AIGC&#xff09;在软件开发领域掀起了一场革命。从代码生成、错误检测到自动化测试&#xff0c;AI工具正在快速改变开发者的工作方式。这些工具不仅提高了开发效率&#xff0c;还引发了关于开发者职业前景和技能需求变化的广泛讨…

Navicat Premium 15 for Mac/Win 中文安装包下载

Navicat Premium 15 是一款数据库管理工具&#xff0c;它支持多种类型的数据库&#xff0c;包括 MySQL、MariaDB、MongoDB、SQL Server、Oracle、PostgreSQL 和 SQLite。该软件提供了一个用户友好的图形界面&#xff0c;使得数据库的管理变得更加简单和高效。Navicat Premium 1…

chrony与ntp两种时钟同步方式对比

chrony 是一个用于网络时间同步的守护进程&#xff0c;设计用来替代传统的 ntpd&#xff08;Network Time Protocol Daemon&#xff09;。虽然两者都基于 NTP&#xff08;网络时间协议&#xff09;来同步系统时钟&#xff0c;但 chrony 在某些方面提供了改进和增强的功能&#…

Python数据分析实战,铁路站点客流量预测,案例教程编程实例课程详解

引言 铁路站点客流量预测是铁路运输管理和优化中的关键任务。准确的客流量预测可以帮助铁路部门提前调配资源,合理安排运力,提高运输效率,减少运营成本,同时提升乘客的出行体验。本文将介绍如何使用Python进行铁路站点客流量的预测,包括数据收集、预处理、模型构建、评估与…

网页视频提取在线工具

在互联网的海洋中&#xff0c;我们时常会遇到一些令人心动的视频&#xff0c;想要将其下载到本地&#xff0c;以便随时观看。然而&#xff0c;网页视频下载对于很多人来说&#xff0c;似乎是个复杂的过程。别担心&#xff0c;今天我就为大家带来一份详尽的网页视频下载教程&…

24小时悬停系留照明无人机技术详解

24小时悬停系留照明无人机是一款专门设计用于提供长时间、高效能照明服务的无人机系统。该系统结合了无人机技术与先进的照明设备&#xff0c;通过系留技术实现无人机的稳定悬停&#xff0c;从而提供连续不断的照明服务。该无人机能够在各种环境条件下进行24小时不间断工作&…

Zkeys三方登录模块支持QQ、支付宝登录

1&#xff0c;覆盖到根目录&#xff0c;并导入update.sql数据库文件到Zkeys数据库里 2. 后台系统权限管理&#xff0c;配置管理员权限-系统类别-找到云外科技&#xff0c;全部打勾 3&#xff0c;后台系统设置找到云外快捷登录模块填写相应的插件授权配置和登录权限配置&#x…

docker 安装教程

机缘 最近在开发用用到了docker,主要是将开发的项目发版到平台上&#xff0c;运用到docker发版&#xff0c;所以才会写这篇文章。 教程 1、安装Hype-v。 在安装之前&#xff0c;首先要检查下电脑系统是否安装Hyper-v功能。 注意&#xff1a;一定要检查电脑系统&#xff0c;…

【React】如何自定义 Hooks

在React中,自定义Hooks允许你将组件逻辑提取到可重用的函数中。自定义Hooks本质上就是普通的JavaScript函数,但是它们必须遵循两个规则: 命名约定:自定义Hook的名称应该以use开头。这个约定有助于你和其他开发者更容易地识别出哪些函数是Hooks。在函数组件内部调用:只能在…

SRC实战:无中生有的接口和参数?

今天分享的这个漏洞怎么说呢&#xff0c;虽然也是个高危&#xff0c;但是其实挺简单的&#xff0c;一个很eazy的越权&#xff0c;但是我觉得多多少少还是有点意思吧。 0x00 这是一个移动端的应用程序&#xff0c;前面比较常规&#xff0c;模拟器 BP&#xff0c;跑了一下所有…

C++:cv::findContours()说明

cv::findContours 是 OpenCV 库中一个非常重要的函数&#xff0c;用于在二值图像中查找轮廓。该函数可以检测图像中对象的边界&#xff0c;并返回这些轮廓的坐标信息&#xff0c;这些轮廓信息通常用于对象检测、分割和形状分析等任务。以下是对 cv::findContours 函数的详细介绍…

多会话 Telnet 日志记录器

创建一个多会话 Telnet 日志记录器可以实现对多个 Telnet 会话进行连接、监控和记录日志。以下是一个基本的 Python 示例&#xff0c;使用 telnetlib 库来实现多会话 Telnet 日志记录器&#xff0c;并使用 threading 模块来处理多个会话。 1、问题背景 我们需要编写一个脚本&a…