死锁简要概述

死锁:两个或两个以上的线程在执行的过程中,由于竞争资源或者彼此等待彼此而造成彼此等待彼此,线程不再往下执行。

根据以上示例图构建连个死锁程序
(1)DeadLock

package com.high.concurrency.currency02.eat;
public class DeadLock extends Thread {

    private String first;
    private String second;
    public DeadLock(String name, String first, String second) {
        super(name);
        this.first = first;
        this.second = second;
    }
    @Override
    public  void run() {
        synchronized (first) {
            try {
                System.out.println(this.getName() + " ...synchronized:===> 【first】" + first);
                Thread.sleep(1000L);
                synchronized (second) {
                    System.out.println(this.getName() + " ...synchronized:===>【second】 " + second);
                }
            } catch (InterruptedException e) {}
        }
    }
    public static void main(String[] args) throws InterruptedException {
        String lockA = "lockA";
        String lockB = "lockB";
        DeadLock t1 = new DeadLock("t1", lockA, lockB);
        DeadLock t2 = new DeadLock("t2", lockB, lockA);
        t1.start();
        t2.start();
        t1.join();
        t2.join();
    }
}
(2)PhilosopherEating
package com.high.concurrency.currency02.eat;


public class PhilosopherEating extends Thread {
    protected Object tool;
    static Object fork1 = new Object();
    static Object fork2 = new Object();


    public PhilosopherEating(Object obj) {
        this.tool = obj;
        if(tool == fork1) {
            this.setName("哲学家A");
        }
        if (tool == fork2) {
            this.setName("哲学家B");
        }
    }


    @Override
    public void run() {
        if(tool == fork1) {
            synchronized (fork1) {
                try {
                    Thread.sleep(500);
                } catch (Exception e) {
                    e.printStackTrace();
                }
                synchronized (fork2) {
                    System.out.println("哲学家A开始吃饭了");
                }
            }
        }


        if (tool == fork2) {
            synchronized (fork2) {
                try {
                    Thread.sleep(500);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }


                synchronized (fork1) {
                    System.out.println("哲学家B开始吃饭了");
                }
            }
        }
    }


    public static void main(String[] args) throws InterruptedException {
        PhilosopherEating philosonpherA = new PhilosopherEating(fork1);
        PhilosopherEating philosonpherB = new PhilosopherEating(fork2);
        philosonpherA.start();
        philosonpherB.start();
        Thread.sleep(1000);
    }

}

上述程序都体现一个特点: 存在两个线程,出现我使用这当前的资源, 申请对方正在使用的资源,而对方尚未释放该资源导致线程阻塞。
查找线程死锁的办法:jps + jstack
首先在终端输入jps,查找到对应的死锁进程号:
8FE61520-601E-489C-A8D8-C37CFBCBF9B5.png

获取到对应的死锁进程,输入jstack + 进程号, 找到对应的报错信息,根据报错信息进行下一步的修改

死锁简要概述_第1张图片
死锁简要概述_第2张图片

你可能感兴趣的:(java)