java并发-ReentrantReadWriteLock

吃透Java并发十四:locks之ReentrantReadWriteLock 一、ReentrantReadWriteLock类简介 ReentrantReadWriteLock类,顾名思义,是一种读写锁,它实现了ReadWriteLock接口,该类在内部实现了具体独占锁特点的写锁,以及具有共享锁特点的读锁,和ReentrantLock一样,ReentrantReadWriteLock类也是通过定义内部类实现AQS框架的API来实现独占/共享的功能。 1、支持公平/非公平策... 阅读详情

ReentrantReadWriteLock 是 Java 并发库中提供的一种可重入的读写锁。与传统的 Mutex 或 ReentrantLock 相比,ReentrantReadWriteLock 允许多个线程同时读取共享资源,但只允许一个线程写入共享资源。这个特性可以提高程序的并发性能,因为读取操作不会发生冲突,可以并发处理。

下面我们来深入了解 ReentrantReadWriteLock 的实现原理和使用方法。

## 实现原理

ReentrantReadWriteLock 的实现基于 AQS(AbstractQueuedSynchronizer),使用了两个内部类 Sync 和 FairSync。其中 Sync 是非公平模式下的同步器,FairSync 是公平模式下的同步器。在 ReentrantReadWriteLock 的构造函数中,可以根据需要选择使用哪种模式。

### 写锁

在使用 ReentrantReadWriteLock 时,如果有线程持有写锁,那么其他线程无法获取读锁或写锁。此时如果有线程请求读锁,会被阻塞;如果有线程请求写锁,也会被阻塞。只有当持有写锁的线程释放锁后,其他线程才有机会获取锁。

### 读锁

如果有线程持有读锁,那么其他线程可以继续获取读锁,但无法获取写锁。只有当没有线程持有读锁时,其他线程才有机会获取写锁。这样做可以保证读锁操作可以并发执行,提高程序的并发性能。

## 使用方法

使用 ReentrantReadWriteLock 非常简单,只需要创建一个 ReentrantReadWriteLock 对象,然后使用 lock() 和 unlock() 方法进行锁操作即可。具体的使用方法如下:

```java
ReentrantReadWriteLock rwl = new ReentrantReadWriteLock();

rwl.readLock().lock();
try {
    // 进行读取操作
} finally {
    rwl.readLock().unlock();
}

rwl.writeLock().lock();
try {
    // 进行写入操作
} finally {
    rwl.writeLock().unlock();
}
```

在使用 ReentrantReadWriteLock 时,需要注意以下几点:

1. 需要显式地调用 lock() 方法进行加锁和 unlock() 方法进行解锁,否则可能会导致死锁和其他问题。
2. 写锁比读锁操作更耗时,因此应该尽量减少写锁操作次数,尽可能多地使用读锁。
3. 由于 ReentrantReadWriteLock 是可重入锁,因此同一个线程可以多次获取同一种类型的锁,不会导致死锁。

## 小结

ReentrantReadWriteLock 是一种可重入的读写锁,可以提高程序的并发性能。在使用它时,需要注意调用 lock() 和 unlock() 方法,尽可能多地使用读锁,减少写锁。同时,也要注意避免死锁等问题。

STM32+OOK通讯(OOK发送+OOK接收)+cubemx配置 关于OOK通信,我的理解就是将要发送的信息转换成高低电平(即0和1),然后接收方通过对01进行解码获得信息。于是我用了非常朴素的字符串转二进制+AM调制来完成通信链。话不多说我们直接开始!!! 阅读详情

相关推荐

CanMV K230实战:用MicroPython玩转AI视觉识别(附完整代码)

本文详细介绍了如何使用MicroPython在CanMV K230开发板上实现AI视觉识别,包括环境搭建、摄像头配置、模型部署及优化技巧。通过实战案例(如智能门禁和工业分拣机器人),展示如何快速开发低门槛的嵌入式AI应用,特别适合初学者和嵌入式开发者。

x8y9z0的博客 1142

Java中读写锁ReadWriteLock的使用案例和性能对比

使用ReentrantReadWriteLock运行的结果为。读写锁与ReentLock锁的效率对比。ReentrantLock运行结果。我们用如下代码进行一个简单的对比。

心比天高,仗剑走天涯,保持热爱,奔赴向梦想! 2209

银河麒麟V10ARM架构服务器离线安装docker\nacos【附安装包】

本文分享了在银河麒麟ARM64操作系统上安装Docker和Nacos的完整过程。首先提供了Docker的自动化安装脚本,包含服务配置、存储路径设置等关键步骤,并给出了常用维护命令。接着详细介绍了通过Docker-compose部署Nacos的方法,包括镜像导入、配置文件修改、鉴权设置等注意事项,特别强调了密钥长度必须超过32个字符的要求。文章还提供了Nacos初次登录的注意事项,并预告了后续可能推出的Redis、Nginx等安装教程。所有配置文件和脚本均可直接下载使用,适合内网环境下国产操作系统的部署

weixin_39054697的博客 2344

ReentrantReadWriteLock详解

之前长时间的面试暴露了一些知识面不够深入,其中一块是ReentrantReadWriteLock读写锁方面,一直没有时间来深入学习,这次补上,关于ReentrantLock的内容可以看一下我前面的文章Java锁详解,里面第二部分详细的介绍了ReentrantLock,废话不多说,直接开始 从前面一文Java锁详解中,分析了以非阻塞同步算法为基础实现的可重入独占锁ReentrantLock。所谓** “独占” 即同一时间只能有一个线程持有锁。而 “重入” **是指该线程如果持有锁,可以在同步代码块内再次请求占

qq_22162093的博客 964

学习海康VisionMaster之路径提取

这里也需要注意下,这里有两种模式,在运行参数的这一栏有“等距离取点”和“查找边缘点”两个检测模式,说实话,那个等距离取点我也没搞懂有什么用,我拿了OK和NG的图片去对比,好像没有什么实际用处,无法检测(不知道有没有小伙伴知道这个模式到底是怎么用的!2:应用场景:典型的场景是点胶检测,判断胶路质量,有没有断胶等,一开始这胶路检测,真的是难倒我了,特别是不规则图像如何检测,学习了这个算子后,思路一下子打开了,原来还可以这么搞!四:实测:上述设定好参数,开始实际测量看看效果,不同的检测模式下的检测效果。

yuhouxiyang的专栏 1483

零基础搭建本地AI绘画环境:Stable Diffusion 3.5保姆级安装教程(含中文优化方案)

本文提供零基础搭建本地AI绘画环境的详细教程,重点介绍Stable Diffusion 3.5的安装与中文优化方案。从硬件配置检查到软件依赖安装,再到核心组件配置与中文语义增强,教程涵盖全流程操作指南,帮助用户快速掌握AI文生图模型的本地部署技巧,提升创作效率。

weixin_30752699的博客 312

Java 并发之 ReentrantReadWriteLock 深入分析

前言 上篇文章分析了AQS的实际应用之一:ReentrantLock 的实现。ReentrantLock 和synchronized 都是独占锁,而AQS还支持共享锁,本篇就来分析AQS 共享锁的实际应用。 通过本篇文章,你将了解到: 1、共享锁、独享锁区别 2、读锁的实现原理 3、写锁的实现原理 4、读写锁 tryLock 原理 5、读写锁的应用 1、共享锁、独享锁区别 基本差别 共享锁、独占锁是在AQS里实现的,核心是"state"的值: 如上图,对于共享锁来说,允许多个线程对state进行有效修

965

【Verilog基础】CDC跨时钟域方法,典型异步电路设计之脉冲同步器(上)

【Verilog基础】CDC跨时钟域方法,典型异步电路设计之脉冲同步器(上):慢时钟域到快时钟域!

悟已往之不谏 知来者之可追 1544

【Java并发】ReentrantReadWriteLock

参考: <<Java并发编程的艺术>> JDK1.8源码 一、读写锁简介 读写锁java.util.concurrent.locks.ReadWriteLock是个接口,接口里定义了两个方法Lock readLock()和Lock writeLock()分别用于获取读锁和写锁。 读写锁(参考ReadWriteLock接口上的注释): 一对锁:读锁用于读操作,写锁用于写操作 读锁:多个读线程可以同时获取到读锁进行读操作,写线程此时获取写锁时会被阻塞 写锁:对于写锁,只有一个

mytt_10566的博客 528

芒果YOLOv5改进05:损失函数IoU 篇之Repulsion Loss:原创改进损失函数 Repulsion:解决目标遮挡场景下检测,为解决密集人群检测中遮挡设计的损失函数,打造高效检测器涨点

YOLOv5改进代码实践|结合Repulsion 解决目标遮挡场景下检测🚀

包括YOLOv5、YOLOv7、YOLOv8等模型改进 4564

使用 MATLAB/Simulink 构建一个 核电站汽轮机与发电机协调控制系统 的仿真模型

在核电机组中,汽轮机-发电机系统是将核能最终转化为电能的关键环节。与火电机组不同,核反应堆的热惯性大、功率调节慢,因此汽轮机的控制策略需与反应堆特性相匹配,实现安全、稳定、高效的能量转换。维持发电机输出功率/频率稳定(响应电网调度)调节汽轮机进汽压力(匹配一回路蒸汽供应)实现“堆-机协调控制”保障机组在启停、变负荷、甩负荷等工况下的安全性本教程将带你使用构建一个核电站汽轮机与发电机协调控制系统汽轮机调速系统(调门控制)建模发电机与电网接口建模(同步机)

xiaoheshang_123的博客 188

java并发之ReentrantReadWriteLock

部分资料来自网络,有版权问题联系我删除 ReentrantReadWriteLock JAVA的并发包提供了读写锁ReentrantReadWriteLock,它表示两个锁,一个是读操作相关的锁,称为共享锁;一个是写相关的锁,称为排他锁,描述如下: 线程进入读锁的前提条件: 没有其他线程的写锁, 没有写请求或者有写请求,但调用线程和持有锁的线程是同一个。 线程进入写锁的前提条件: 没有其他线程的读锁 没有其他线程的写锁 而读写锁有以下三个重要的特性: (1)公平选择性:支持非公平(

weixin_54558363的博客 132

深度学习工具包 DeepLearningToolbox

深度学习工具包Deprecation notice.-----This toolbox is outdated and no longer maintained.There are much better tools available for deep learning than this toolbox, e.g. [Theano](http://deeplearning.net/software/theano/), [torch](http://torch.ch/) or [tensorflow](http://www.tensorflow.org/)I would suggest you use one of the tools mentioned above rather than use this toolbox.Best, Rasmus.DeepLearnToolbox================A Matlab toolbox for Deep Learning.Deep Learning is a new subfield of machine learning that focuses on learning deep hierarchical models of data.It is inspired by the human brain's apparent deep (layered, hierarchical) architecture.A good overview of the theory of Deep Learning theory is[Learning Deep Architectures for AI](http://www.iro.umontreal.ca/~bengioy/papers/ftml_book.pdf)For a more informal introduction, see the following videos by Geoffrey Hinton and Andrew Ng.* [The Next Generation of Neural Networks](http://www.youtube.com/watch?v=AyzOUbkUf3M) (Hinton, 2007)* [Recent Developments in Deep Learning](http://www.youtube.com/watch?v=VdIURAu1-aU) (Hinton, 2010)* [Unsupervised Feature Learning and Deep Learning](http://www.youtube.com/watch?v=ZmNOAtZIgIk) (Ng, 2011)If you use this toolbox in your research please cite [Prediction as a candidate for learning deep hierarchical models of data](http://www2.imm.dtu.dk/pubdb/views/publication_details.php?id=6284)```@MASTERSTHESIS\{IMM2012-06284, author = "R. B. Palm", title = "Prediction as a candidate for learning deep hierarchical models of data", year = "2012",}```Contact: rasmusbergpalm at gmail dot comDirectories included in the toolbox-----------------------------------`NN/` - A library for Feedforward Backpropagation Neural Networks`CNN/` - A library for Convolutional Neural Networks`DBN/` - A library for Deep Belief Networks`SAE/` - A library for Stacked Auto-Encoders`CAE/` - A library for Convolutional Auto-Encoders`util/` - Utility functions used by the libraries`data/` - Data used by the examples`tests/` - unit tests to verify toolbox is workingFor references on each library check REFS.mdSetup-----1. Download.2. addpath(genpath('DeepLearnToolbox'));Example: Deep Belief Network---------------------```matlabfunction test_example_DBNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit RBM and visualize its weightsrand('state',0)dbn.sizes = [100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);figure; visualize(dbn.rbm{1}.W'); % Visualize the RBM weights%% ex2 train a 100-100 hidden unit DBN and use its weights to initialize a NNrand('state',0)%train dbndbn.sizes = [100 100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);%unfold dbn to nnnn = dbnunfoldtonn(dbn, 10);nn.activation_function = 'sigm';%train nnopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.10, 'Too big error');```Example: Stacked Auto-Encoders---------------------```matlabfunction test_example_SAEload mnist_uint8;train_x = double(train_x)/255;test_x = double(test_x)/255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit SDAE and use it to initialize a FFNN% Setup and train a stacked denoising autoencoder (SDAE)rand('state',0)sae = saesetup([784 100]);sae.ae{1}.activation_function = 'sigm';sae.ae{1}.learningRate = 1;sae.ae{1}.inputZeroMaskedFraction = 0.5;opts.numepochs = 1;opts.batchsize = 100;sae = saetrain(sae, train_x, opts);visualize(sae.ae{1}.W{1}(:,2:end)')% Use the SDAE to initialize a FFNNnn = nnsetup([784 100 10]);nn.activation_function = 'sigm';nn.learningRate = 1;nn.W{1} = sae.ae{1}.W{1};% Train the FFNNopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.16, 'Too big error');```Example: Convolutional Neural Nets---------------------```matlabfunction test_example_CNNload mnist_uint8;train_x = double(reshape(train_x',28,28,60000))/255;test_x = double(reshape(test_x',28,28,10000))/255;train_y = double(train_y');test_y = double(test_y');%% ex1 Train a 6c-2s-12c-2s Convolutional neural network %will run 1 epoch in about 200 second and get around 11% error. %With 100 epochs you'll get around 1.2% errorrand('state',0)cnn.layers = { struct('type', 'i') %input layer struct('type', 'c', 'outputmaps', 6, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %sub sampling layer struct('type', 'c', 'outputmaps', 12, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %subsampling layer};cnn = cnnsetup(cnn, train_x, train_y);opts.alpha = 1;opts.batchsize = 50;opts.numepochs = 1;cnn = cnntrain(cnn, train_x, train_y, opts);[er, bad] = cnntest(cnn, test_x, test_y);%plot mean squared errorfigure; plot(cnn.rL);assert(er<0.12, 'Too big error');```Example: Neural Networks---------------------```matlabfunction test_example_NNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);% normalize[train_x, mu, sigma] = zscore(train_x);test_x = normalize(test_x, mu, sigma);%% ex1 vanilla neural netrand('state',0)nn = nnsetup([784 100 10]);opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samples[nn, L] = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.08, 'Too big error');%% ex2 neural net with L2 weight decayrand('state',0)nn = nnsetup([784 100 10]);nn.weightPenaltyL2 = 1e-4; % L2 weight decayopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex3 neural net with dropoutrand('state',0)nn = nnsetup([784 100 10]);nn.dropoutFraction = 0.5; % Dropout fraction opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex4 neural net with sigmoid activation functionrand('state',0)nn = nnsetup([784 100 10]);nn.activation_function = 'sigm'; % Sigmoid activation functionnn.learningRate = 1; % Sigm require a lower learning rateopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex5 plotting functionalityrand('state',0)nn = nnsetup([784 20 10]);opts.numepochs = 5; % Number of full sweeps through datann.output = 'softmax'; % use softmax outputopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex6 neural net with sigmoid activation and plotting of validation and training error% split training data into training and validation datavx = train_x(1:10000,:);tx = train_x(10001:end,:);vy = train_y(1:10000,:);ty = train_y(10001:end,:);rand('state',0)nn = nnsetup([784 20 10]); nn.output = 'softmax'; % use softmax outputopts.numepochs = 5; % Number of full sweeps through dataopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, tx, ty, opts, vx, vy); % nntrain takes validation set as last two arguments (optionally)[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');```[![Bitdeli Badge](https://d2weczhvl823v0.cloudfront.net/rasmusbergpalm/deeplearntoolbox/trend.png)](https://bitdeli.com/free "Bitdeli Badge")

Java并发中的ReentrantReadWriteLock

1.背景介绍 Java并发中的ReentrantReadWriteLock 1. 背景介绍 在Java并发中,读写锁(ReadWriteLock)是一种用于控制多个线程对共享资源的访问的锁机制。它允许多个线程同时进行只读操作,但在进行写操作时,其他线程无法访问该资源。这种锁机制有助于提高并发性能,减少锁竞争。 ReentrantReadWriteLock是Java并发包中的一种读写锁实现,...

AI天才研究院 877

LinePhone3.2.7(android端最新版本) sip客户端

SIP客户端For android:LinePhone3.2.7(最新版本),官网地址:http://www.linphone.org/

最新的sdio 4.0 spec 协议标准 带书签 高清完整PDF版

Part-E1-SDIO-Specification-Ver4.00-Final-120220.pdf:最新的sdio 4.0 spec 协议标准 带书签 高清完整PDF版,包括SDIO 接口的外设,SDIO 接口官方协议等。

Java并发编程之ReentrantReadWriteLock

Java并发编程之ReentrantReadWriteLock 概述: ReentrantReadWriteLock是Lock的另一种实现方式,我们已经知道了ReentrantLock是一个排他锁,同一时间只允许一个线程访问,而ReentrantReadWriteLock允许多个读线程同时访问,但不允许写线程和读线程、写线程和写线程同时访问。相对于排他锁,提高了并发性。在实际应用中,大部分情况下对共享数据(如缓存)的访问都是读操作远多于写操作,这时ReentrantReadWriteLock能够提供比排他

zdl_csdn的博客 161

Java内置锁:深度解析ReentrantReadWriteLock并发类

ReentrantLock和ReentrantReadWriteLock是Java中用于线程同步的重要工具。ReentrantLock提供独占访问,适合需要保护共享资源不被并发修改的场景,同时支持可重入性,适用于递归操作。而ReentrantReadWriteLock则通过读写分离,允许多个线程同时读取资源,但仅允许一个线程写入,从而提高了并发性能。这种锁机制在处理大量读操作和较少写操作的场景中尤为有效。

科技互联网领域深度探索者,乐于分享与写作。 1035

[java并发]读写锁ReentrantReadWriteLock里面的FairSync 和 NonfairSync

背景介绍 最近转行做java后台了,对于java的并发完全不熟悉,于是到网上各种搜资料。 接到的一个任务是一个很简单从数据库里面读取一些表到内存里面,然后做一个缓存。 读数据库用的EJB3的Entity Bean; 服务是基于JBoss的MBean;访问接口是EJB3的stateless session bean; 因为session bean是多线程的方式访问Mbean的,所以要考虑内存

lucifer545的专栏 3029

Java并发源码分析之ReentrantReadWriteLock

目录工作原理概要类图原理概述Sync关键常量内部类关键变量读锁/写锁计算方法ReadLock获取读锁流程1、ReadLock–获取锁入口2、AQS–acquireShared获取共享锁3、Sync–tryAcquireShared尝试获取共享锁 工作原理概要 ReentrantReadWriteLock是基于AQS框架构建的,相关类图如下: 类图 AbstractOwnableSynchronizer:抽象类,定义了独占锁线程,exclusiveOwnerThread AbstractQueuedSync

Murphy_H的博客 997

Java并发学习笔记16 AQS 之 ReentrantReadWriteLock

bilibili-Java并发学习笔记16 AQS 之 ReentrantReadWriteLock 基于 java 1.8.0 P48_可重入读写锁底层源码分析及思想探究 // ReadWriteLock 使用示例 package new_package.thread.p45; import java.util.concurrent.TimeUnit; import java.util.concurrent.locks.ReadWriteLock; import java.util.concurrent

晨猫 222

Java并发之-读写锁ReentrantReadWriteLock

前言 之前提到的ReentrantLock是排他锁,这种锁同一时刻只允许一个线程访问,而读写锁同一时刻可以多个线程访问,但在写线程访问时,所有读线程和其他写线程都要被阻塞。读写锁维护了一对锁,一个读锁和一个写锁,通过分离读写锁,使得并发性相比一般的排他锁有很大提升。 参考文献 《Java并发编程的艺术》 正文 读写锁只需要在读操作时获取读锁,写操作获取写锁即可。当写操作被获取时,后续读写...

晏霖/胖虎的博客 4679

【并发编程】java并发编程之ReentrantReadWriteLock读写锁

log.info(“缓存中没有数据,往数据库获取”);//缓存中没有数据,从数据库捞取数据(这里我就不去数据库拿了,直接用map集合模拟)if(null!= user){//将数据存到缓存中这是一个获取用户信息的方法,模拟了先从缓存中获取数据,如果缓存中不存在,则向数据库中获取,这段代码看起来因该是没有任何问题,但事实是这样吗?我们来测试一下,使用jmeter做并发测试:模拟一百个线程同时访问,结果会是如何呢?

2401_84103844的博客 312

Java并发编程一ReentrantReadWriteLock初使用

Java并发编程一ReentrantReadWriteLock初使用 ReentrantReadWriteLock是一种读写锁,从类名也可以看出来。 ReentrantReadWriteLock类有两个属性ReentrantReadWriteLock.ReadLock readerLock(代表读锁)、ReentrantReadWriteLock.WriteLock writerLock(代表写锁...

kaven 1046

java并发编程——ReentrantReadWriteLock和StampedLock

ReentrantReadWriteLock和StampedLock简介

weixin_64451672的博客 542

Java并发学习笔记15 ReentrantReadWriteLock 概览

bilibili-Java并发学习笔记15 ReentrantReadWriteLock 概览 基于 java 1.8.0 package java.util.concurrent.locks; /** * ReadWriteLock 维护了一对相关的锁,一个用于只读操作,另一个用于写入操作。 * 只要没有 writer,读取锁可以由多个 reader 线程同时保持。写入锁是独占的。 * * 所有 ReadWriteLock 实现都必须保证 writeLock 操作的内存同步效果 * 也要保持与

晨猫 176

深入理解Java并发读写锁——ReentrantReadWriteLock

若当前线程不是第一个读线程,那么首先会获取缓存计数器(上一个读锁线程对应的计数器 ),若计数器为空或者tid不等于当前线程的tid值,则获取当前线程的计数器,如果计数器的计数count小于等于1,则移除当前线程对应的计数器,如果计数器的计数count小于等于0,则抛出异常,之后再减少计数即可。如果当前线程获取读锁,即遵循锁降级的步骤,则线程T将会被阻塞,直到当前线程使用数据并释放读锁之后,线程T才能获取写锁进行数据更新。若存在,则需要被阻塞,否则,无需阻塞),之后在设置状态state,然后返回true。

sdgfafg_25的博客 978

java readandwrite_Java并发之ReentrantReadWriteLock设计实现详解

概述维护了一对关联的锁,一个用于只读操作,另一个用于写操作。其中写锁是独占的,只要没有写操作,多个读线程可以同时持有读锁。也就是说,成功获取读锁的线程将看到在先前的写锁上所做的所有更新。1、不频繁写,频繁读,适合使用读写锁。否则,大部分时间会被写锁独占。2、如果读操作过于短,则读写锁的实现会占用绝大部分性能开销,因为比一般的互斥锁执行逻辑更复杂。变量含义理解下面的变量含义,有助于理解代码。Stat...

weixin_36364707的博客 190
上一篇: java并发-ReentrantLock
下一篇: java并发-Condition
曲终--人散
博客等级 码龄14年 23粉丝 51原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值