Java创建基本的死锁系统

示例

当两个竞争性动作等待另一个动作完成时,就会发生死锁,因此两者都不会。在Java中,每个对象都有一个锁。为了避免多个线程对单个对象进行并发修改,我们可以使用synchronized关键字,但是一切都是有代价的。synchronized错误使用关键字会导致卡死的系统,称为死锁系统。

考虑在一个实例上有2个线程工作,让线程分别称为First和Second,并说我们有2个资源R1和R2。首先获取R1并需要R2来完成它,而第二获取R2并需要R1来完成。

假设在时间t = 0,

第一个具有R1,第二个具有R2。现在,First在等待R2,而Second在等待R1。此等待是不确定的,这将导致死锁。

public class Example2 {
    
    public static void main(String[] args) throws InterruptedException {
        final DeadLock dl = new DeadLock();
        Thread t1 = new Thread(new Runnable() {
    
            @Override
            public void run() {
                // TODO自动生成的方法存根
                dl.methodA();
            }
        });
   
        Thread t2 = new Thread(new Runnable() {
    
            @Override
            public void run() {
                // TODO自动生成的方法存根
                try {
                    dl.method2();
                } catch (InterruptedException e) {
                    // TODO自动生成的捕获块
                    e.printStackTrace();
                }
            }
        });
        t1.setName("First");
        t2.setName("Second");
        t1.start();
        t2.start();
    }
}

class DeadLock {
    
    Object mLock1 = new Object();
    Object mLock2 = new Object();
    

    public void methodA() {
        System.out.println("方法A等待mLock1  " + Thread.currentThread().getName());
        synchronized (mLock1) {
            System.out.println("方法获得了一个mLock1   " + Thread.currentThread().getName());
            try {
                Thread.sleep(100);
                method2();
            } catch (InterruptedException e) {
                // TODO自动生成的捕获块
                e.printStackTrace();
            }
        }
    }
    public void method2() throws InterruptedException {
        System.out.println("method2等待mLock2  " + Thread.currentThread().getName());
        synchronized (mLock2) {
            System.out.println("方法2获得了mLock2   " + Thread.currentThread().getName());
            Thread.sleep(100);
            method3();
        }
    }
    public void method3() throws InterruptedException {
        System.out.println("方法3 mLock1  "+ Thread.currentThread().getName());
        synchronized (mLock1) {
            System.out.println("方法3获得了mLock1  " + Thread.currentThread().getName());
        }
    }
}

该程序的输出:

方法A等待mLock1  First
method2等待mLock2  Second
方法2获得了mLock2   Second
方法获得了一个mLock1   First
方法3 mLock1  Second
method2等待mLock2  First