ReentrantLock锁


ReentrantLock是可重入锁,并且可以实现公平锁。Sychronized是可重入锁、非公平锁。

话不多说,上demo:

 1 package com.example.demo.util;
 2 
 3 import java.util.concurrent.locks.ReentrantLock;
 4 
 5 public class ReetrantLockFairTest {
 6 
 7     // 参数为true,则为公平锁,即线程按等待时间顺序,最久的先获得锁
 8     // 参数为false或为空则为非公平锁,线程自由竞争锁
 9     static ReentrantLock lock = new ReentrantLock(true);
10 
11     public static void main(String[] args) {
12 
13         for (int i = 0; i < 8; i++) {
14             new Thread(() -> test(), "线程" + i).start();
15         }
16     }
17 
18     public static void test() {
19 
20         for (int i = 0; i < 2; i++) {// 使用循环2轮并且加sleep时间,来模拟测试线程执行顺序
21             lock.lock();
22             try {
23                 System.out.println(Thread.currentThread().getName() + ":获得了锁。");
24                 Thread.sleep(500l);// 模拟时间需确保第一个线程获得锁后,其他所有线程都已经启动并等待锁。然后进入for循环等待第二轮
25             } catch (Exception e) {
26                 e.printStackTrace();
27             } finally {
28                 lock.unlock();
29             }
30         }
31     }
32 }

执行结果:可以看到,第二轮获得锁的线程顺序与第一轮 一样。这样就实现了公平锁。

线程0:获得了锁。
线程2:获得了锁。
线程1:获得了锁。
线程3:获得了锁。
线程4:获得了锁。
线程5:获得了锁。
线程6:获得了锁。
线程7:获得了锁。
线程0:获得了锁。 线程2:获得了锁。 线程1:获得了锁。 线程3:获得了锁。 线程4:获得了锁。 线程5:获得了锁。 线程6:获得了锁。 线程7:获得了锁。