Java--JUC--公平锁,非公平锁,可重入锁,自旋锁,死锁
- 公平锁
- 非公平锁
- 可重入锁(递归锁)
-
package com.model.lock; import java.util.concurrent.TimeUnit; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /** * @Description:测试类 * @Author: 张紫韩 * @Crete 2021/6/10 16:14 */ public class LockDemo { /** * 1.公平锁,非公平锁 * 公平锁:不允许插队 * 公平锁:允许插队 * public ReentrantLock(boolean fair) { * sync = fair ? new FairSync() : new NonfairSync(); * } * 2.可重入锁(递归锁) * 拿到外面的锁,就会自动获得里面的锁(大门得锁,和卧室得锁) * 外面的锁,包含里面的锁,只有当里面得锁释放之后,外面得锁锁才能释放 * 是一种包含关系,先拿到后释放,后拿到先释放 * * 3.自旋锁 * 4.死锁 * */ public static void main(String[] args) { /* Lock lock=new ReentrantLock(true); //公平锁 Lock lock1=new ReentrantLock();//非公平锁,默认 */ Phone phone=new Phone(); new Thread(() ->{ phone.msg(); },"A").start(); new Thread(() ->{ phone.msg(); },"B").start(); } } class Phone{ //lock锁必须进行配对操作,上锁和解锁的相对应 Lock lock=new ReentrantLock(); public void msg(){ lock.lock(); try { System.out.println(Thread.currentThread().getName()+"执行了msg"); TimeUnit.SECONDS.sleep(2); call(); }catch (Exception e){ e.printStackTrace(); }finally { lock.unlock(); } } public void call(){ lock.lock(); try { System.out.println(Thread.currentThread().getName()+"执行了call"); }catch (Exception e){ e.printStackTrace(); }finally { lock.unlock(); } } }
- 自旋锁
-
-
package com.model.lock; import java.util.ArrayList; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicReference; /** * @Description:测试类 * @Author: 张紫韩 * @Crete 2021/6/10 17:08 */ public class SpinLockDemo { //在类里面创建接口,类不能使用new 类名(),在使用快捷键形成变量的方式 AtomicReference<Thread> atomicReference=new AtomicReference<>(); public void myLock(){ Thread thread = Thread.currentThread(); // System.out.println(Thread.currentThread().getName()+"开始获取锁操作"); //加锁, 如果一直获取不到锁,就会一直在这里转,自旋,知道拿到锁 while (!atomicReference.compareAndSet(null, thread)){}; System.out.println(Thread.currentThread().getName()+"获得了锁"); } public void myUnLock(){ Thread thread=Thread.currentThread(); if (atomicReference.compareAndSet(thread, null)){ System.out.println(Thread.currentThread().getName()+"释放锁成功"); } } } class TestSpinLock{ public static void main(String[] args) { SpinLockDemo spinLockDemo=new SpinLockDemo(); new Thread(() ->{ spinLockDemo.myLock(); try { TimeUnit.SECONDS.sleep(3); } catch (InterruptedException e) { e.printStackTrace(); } spinLockDemo.myUnLock(); },"A").start(); new Thread(() ->{ try { TimeUnit.SECONDS.sleep(1); } catch (InterruptedException e) { e.printStackTrace(); } spinLockDemo.myLock(); try { TimeUnit.SECONDS.sleep(3); } catch (InterruptedException e) { e.printStackTrace(); } spinLockDemo.myUnLock(); },"B").start(); } }
-
- 死锁
-
package com.model.lock; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicReference; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /** * @Description:测试类 * @Author: 张紫韩 * @Crete 2021/6/10 16:14 */ public class LockDemo { /** * 1.公平锁,非公平锁 * 公平锁:不允许插队 * 公平锁:允许插队 * public ReentrantLock(boolean fair) { * sync = fair ? new FairSync() : new NonfairSync(); * } * 2.可重入锁(递归锁) * 拿到外面的锁,就会自动获得里面的锁(大门得锁,和卧室得锁) * 外面的锁,包含里面的锁,只有当里面得锁释放之后,外面得锁锁才能释放 * 是一种包含关系,先拿到后释放,后拿到先释放 * * 3.自旋锁 * 4.死锁 * */ public static void main(String[] args) { /* Lock lock=new ReentrantLock(true); //公平锁 Lock lock1=new ReentrantLock();//非公平锁,默认 */ Phone phone=new Phone(); new Thread(() ->{ phone.msg(); },"A").start(); new Thread(() ->{ phone.msg(); },"B").start(); } } class Phone{ //lock锁必须进行配对操作,上锁和解锁的相对应 Lock lock=new ReentrantLock(); public void msg(){ lock.lock(); try { System.out.println(Thread.currentThread().getName()+"执行了msg"); TimeUnit.SECONDS.sleep(2); call(); }catch (Exception e){ e.printStackTrace(); }finally { lock.unlock(); } } public void call(){ lock.lock(); try { System.out.println(Thread.currentThread().getName()+"执行了call"); }catch (Exception e){ e.printStackTrace(); }finally { lock.unlock(); } } }
- 解决方式,配查问题:
- 查看日志
- 查看堆栈信息
- 使用 :jps -l ,查看当前运行的进程号
- 使用 jstack 死锁进程号,查看堆栈信息
-