您好,欢迎来到锐游网。
搜索
您的当前位置:首页JAVA多线程高并发之ReentrantLock讲解lockInterruptibly方法

JAVA多线程高并发之ReentrantLock讲解lockInterruptibly方法

来源:锐游网

JAVA中多线程高并发场景下保证线程安全通常都会考虑加锁。但是在特殊场景下我们也可以采用java.util.concurrent包提供的线程安全的对象,避免加锁从而达到高效的目的。

但是,这些线程安全的对象仅仅指的是针对于原子性操作是线程安全的,如果多个方法同时调用无法保证线程安全,只能考虑加锁。这里我们举个列子:假设我们在多线程高并发场景下使用java.util.concurrent.ConcurrentLinkedQueue这个对象来获取队列中的元素,可以直接调用poll()方法,不用加锁也可以保证线程安全,假如我们在获取的时候需要先判断队列是否为空然后获取,也就是先调用isEmpty()方法、接着调用poll()方法,这种情况就无法保证线程安全,因为这里是两步操作,无法保证原子性。

ReentrantLock也是多线程并发时候加锁一种方式,通常会用来和synchronized做比较。我简单整理一下如下:

1、从使用方法角度对比

2、从性能角度对比

  1. JDK1.5以前synchronized性能略低于ReentrantLock,包含JDK1.5版本
  2. JDK1.5以后Java虚拟机对synchronized做了很多优化,增加了偏向锁、轻量级锁(多数情况下是自旋锁)、重量级锁等细节。性能和ReentrantLock差不多。

我们来分析ReentrantLock 调用lockInterruptibly方法,可以对线程interrupt方法做成响应

package com.reentranlock;

import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * ReentrantLock还可以调用lockInterruptibly方法,可以对线程interrupt方法做成响应
 *
 * @author 小辉哥/小辉GE
 * <p>
 * 2019年8月10日 下午15:30:00
 */
public class ReentrantLockInterrupt {

	public static void main(String[] args) {
		Lock lock = new ReentrantLock();
		Thread thread1 = new Thread(() -> {
			lock.lock();
			try {
				System.out.println("thread1 start......");
				TimeUnit.SECONDS.sleep(Integer.MAX_VALUE);
			} catch (InterruptedException e) {
				System.out.println("thread1" + "interrupt......");
			} finally {
				lock.unlock();
				System.out.println("thread1 end......");
			}
		});
		thread1.start();

		Thread thread2 = new Thread(() -> {
			boolean status = false;
			try {
				status = lock.tryLock();
				System.out.println("thread2 start......");
				// 可以对interrupt方法做出响应
				if (!status)
					lock.lockInterruptibly();
			} catch (InterruptedException e) {
				System.out.println("thread2" + "interrupt");
			} finally {
				if (status)
					lock.unlock();
				System.out.println("thread2 end");
			}
		});
		thread2.start();

		try {
			TimeUnit.SECONDS.sleep(5);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}

		thread2.interrupt();
	}

}

测试输出结果如下:

结果分析:

thread1 和 thread2两个线程启动,thread1 sleep很久,thread2调用lockInterruptibly方法,可以对线程interrupt方法做成响应,直接结束。这就是ReentrantLock可以对等待的线程进行打断,很强悍吧。

以上代码仅供参考,如有不当之处,欢迎指出!!!

更多干货,欢迎大家关注和联系我。期待和大家一起更好的交流、探讨技术!!!

 

因篇幅问题不能全部显示,请点此查看更多更全内容

Copyright © 2019- ryyc.cn 版权所有 湘ICP备2023022495号-3

违法及侵权请联系:TEL:199 1889 7713 E-MAIL:2724546146@qq.com

本站由北京市万商天勤律师事务所王兴未律师提供法律服务