死锁定义:死锁是指两个或两个以上的进程在执行过程当中,因为竞争资源或者因为彼此通讯而形成的一种阻塞现象,若无外力做用,它们都将没法推动下去,此时称系统处于死锁状态或系统产生了死锁,这些永远在相互等待的进程称为死锁进程。ide
例子:哲学家进餐问题函数
死锁产生的必要条件:this
破坏产生死锁的任何一个必要条件均可以消除死锁现象。spa
写一个简单的死锁程序:线程
package com.fpc.Test; class thread1 implements Runnable { private DeadLock deadlock; //构造函数 public thread1( DeadLock deadlock ) { this.deadlock = deadlock; } @Override public void run( ) { try { deadlock.lock1toLock2(); } catch( Exception e ) { e.printStackTrace(); } } } class thread2 implements Runnable { private DeadLock deadlock; //构造函数 public thread2( DeadLock deadlock ) { this.deadlock = deadlock; } @Override public void run( ) { try { deadlock.lock2toLock1(); } catch( Exception e ) { e.printStackTrace(); } } } public class DeadLock { private Object lock1 = new Object(); private Object lock2 = new Object(); public void lock1toLock2() { synchronized( lock1 ) { try { Thread.sleep(2000); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } synchronized( lock2 ) { System.out.println("lock1toLock2 end....."); } } } public void lock2toLock1() { synchronized( lock2 ) { try { Thread.sleep(2000); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } synchronized( lock1 ) { System.out.println("lock2toLock1 end....."); } } } public static void main( String[] args ) { DeadLock d = new DeadLock(); thread1 t1 = new thread1(d); thread2 t2 = new thread2(d); Thread th1 = new Thread(t1); Thread th2 = new Thread(t2); th1.start(); th2.start(); } }
怎么去分析死锁:设计
先用jps命令查看虚机中运行的Java线程的pid:3d
而后根据pid 去查看 jstack pid:code
避免死锁的方式对象
1.设计时考虑清楚锁的顺序,尽可能减小嵌套的加锁交互数量blog
2.死锁产生的缘由是资源的循环等待,那么给获取锁加个时间限制,超过必定的时间尚未获取到对象的锁,那么就释放已经获取的对象的锁。固然synchronized是没法作到的,能够用可重入锁ReentrantLock
针对上面的程序能够这么改:
public void lock1toLock2() throws InterruptedException { if (lock1.tryLock(3000, TimeUnit.MILLISECONDS)){ try { Thread.sleep(2000); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } try { if ( lock2.tryLock(3000, TimeUnit.MICROSECONDS) ) { System.out.println("lock1toLock2 end....."); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } }
运行再次查看jps:能够看到没有出现DeadLock线程了,嗯,不会出现死锁了