AQS同步组件(二)

java中锁主要分为两类: 1、 synchronized 关键字修饰的锁   2、 在同步容器JUC中 ReentrantLock(可重入性) 关键字修饰的锁

ReenTrantLock 和 synchronized 的区别:

1、可重入性 ,两者都是一样的,当有线程进入锁,计数器就加1,当计数器为0的时候,释放锁

2、 锁的实现 ,Synchronized 锁是基于jvm实现的 ,而ReenTrantLock是基于JDK实现的

3、性能的区别 ,在synchronized进行性能优化之后,两者之间的区别是很小的,更建议使用synchronized,因为实现起来更为简单

4、 功能的区别:  synchronized使用起来更加的方便和便捷,是由JVM实现加锁的,而reenTrantLock是需要通过代码实现加锁机制的 ,在锁的细粒度和灵活性方面reentrantLock是由于Synchronized的

ReenTrantLock独有的功能:

1、 ReenTrantLock 可以指定是公平锁还是非公平锁 ,synchronized只能是非公平锁 ,所谓的公平锁就是先等待的线程先获得锁

2、提供了一个condition类,可以实现分组唤醒需要唤醒的线程

3、 提供了能够中断等待锁的线程的机制,lock.lockinterruptibly

ReenTrantLock 代码示例:

package MyStudyTest.LOck;

import com.mmall.concurrency.annoations.ThreadSafe;
import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

@Slf4j
@ThreadSafe
public class LockExample1 {
    //总请求数
    private static int clientTotal = 5000;

    //总的并发请求数
    private static int threadTotal = 200;

    private static int count = 0;

    private final static Lock lock = new ReentrantLock();
    public static void main(String[] args) throws InterruptedException {
        //创建一个动态可变长线程池
        ExecutorService executorService = Executors.newCachedThreadPool();
        CountDownLatch countDownLatch = new CountDownLatch(clientTotal) ;
        Semaphore sema = new Semaphore(threadTotal);

        for (int i =0; i<clientTotal; i++ ){
            executorService.execute(()->{
                try {
                    sema.acquire();
                    add();
                    sema.release();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }finally{
                    countDownLatch.countDown();
                }
            });
        }
        countDownLatch.await();
        executorService.shutdown();
        log.info("count:{}", count);
        }
    private  static void add() {
        lock.lock();
        try {
            count++;
        }finally{
            lock.unlock();
        }
    }

    }

关于ReenTrantLock 中一些方法的使用: (提供了很多线程操作的函数 )

1、 trylock ()    --: 仅当线程调用时锁定未被另一个线程调用的情况下才获取锁定

2、lockinteruptibly : 只有当当前线程没有被中断的情况下,才获取锁定 ,如果线程中断了,就抛出异常

ReenTrantReadWriteLock : 当没有任何读写锁的时候,才获取锁

原文地址:https://www.cnblogs.com/wcgstudy/p/11516968.html

时间: 2024-10-30 05:28:29

AQS同步组件(二)的相关文章

AQS 原理以及 AQS 同步组件总结

1 AQS 简单介绍 AQS 的全称为(AbstractQueuedSynchronizer),这个类在 java.util.concurrent.locks 包下面. AQS 是一个用来构建锁和同步器的框架,使用 AQS 能简单且高效地构造出应用广泛的大量的同步器,比如我们提到的 ReentrantLock,Semaphore,其他的诸如 ReentrantReadWriteLock,SynchronousQueue,FutureTask 等等皆是基于 AQS 的.当然,我们自己也能利用 AQ

AQS 同步组件学习(一)

CountDownLatch 实例代码: package com.mmall.concurrency.example.aqs; import lombok.extern.slf4j.Slf4j; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; @Slf4j public class Coun

Java显式锁学习总结之二:使用AbstractQueuedSynchronizer构建同步组件

Jdk1.5中包含了并发大神Doug Lea写的并发工具包java.util.concurrent,这个工具包中包含了显示锁和其他的实用同步组件.Doug Lea在构建锁和组件的时候,大多是以队列同步器(AbstractQueuedSynchronizer)为基础的,因此AbstractQueuedSynchronizer可以看作是并发包的基础框架.因此掌握了AbstractQueuedSynchronizer的实现原理,也就掌握了大多数并发组件的实现原理. AbstractQueuedSync

AQS的几个同步组件

AQS的几个同步组件 CountDownLatch 一个线程或多个线程一直等待,直到其他线程执行的操作完成才继续执行. 应用:并行计算. 计数器是不能重计的,计数值不能往上加,类似操作只有一次. 使用时首先new一个countDownLatch,构造方法中放入计数,然后在一个线程中调用await方法,这个线程就会进入等待状态,其他线程中调用countDown方法减少这个计数,直至降到0时,await方法阻塞的线程会被唤醒继续工作,为保证顺利执行,countDown方法一定要放在finally块里

AQS同步队列器之一:介绍以及简单使用

一.简介 JDK1.5之前都是通过synchronized关键字实现并发同步,而JDK1.5以后Doug Lea大师开发了current包下的类,通过JAVA代码实现了synchronized关键的语义.然而在current包下的这些类的实现大部分都不离不开一个基础组件----AQS(AbstractQueuedSynchronizer)也就是同步队列器. AQS定义了一套多线程访问共享资源的同步框架,比如ReentrantLock.CountDownLatch等都是依赖这个基础组件实现的.深入

JUC之LockSupport构建同步组件的基本工具

一.前言 LockSupport工具类用于阻塞或唤醒线程.LockSupport定义了一组的公共静态方法,这些方法提供了最基本的线程组阻塞和唤醒功能,而LockSupport也成为构建同步组件的基础工具. LockSupport定义了一组以park开头的方法用来阻塞当前线程,以及unpark(Thread thread)方法来唤醒一个被阻塞的线程. 二.源码分析 2.1 属性 public class LockSupport { // Hotspot implementation via int

从零开始学android&lt;RatingBar评分组件.二十三.&gt;

如果现在用户要对某个应用程序打分往往会使用图所示的组件,通过选择的"五角星"的个数来决定最终的打分成绩 这样的功能在Android之中,可以使用RatingBar组件实现,使用此组件可以方便用户的输入,而且很直观,RatingBar类的定义结构如下: java.lang.Object ? android.view.View ? android.widget.ProgressBar ? android.widget.AbsSeekBar ? android.widget.RatingBa

java实现自定义同步组件的过程

实现同步组件twinsLock:可以允许两个线程同时获取到锁,多出的其它线程将被阻塞. 以下是自定义的同步组件类,一般我们将自定义同步器Sync定义为同步组件TwinsLock的静态内部类. 实现同步器需要继承AbstractQueuedSynchronizer并覆盖相应的方法. package com.lock; import java.util.concurrent.TimeUnit;import java.util.concurrent.locks.AbstractQueuedSynchr

从零开始学android&lt;ImageSwitcher图片切换组件.二十六.&gt;

ImageSwitcher组件的主要功能是完成图片的切换显示,例如用户在进行图片浏览的时候,可以通过按钮点击一张张的切换显示的图片,而且使用ImageSwitcher组件在每次切换的时候也可以为其增加一些动画的效果,此类定义如下: java.lang.Object ? android.view.View ? android.view.ViewGroup ? android.widget.FrameLayout ? android.widget.ViewAnimator ? android.wid