使用lock演示死锁
package lock的使用; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; public class 死锁 { public static void main(String[] args) { Lock lockA = new ReentrantLock(); Lock lockB = new ReentrantLock(); Thread t1 = new Thread() { @Override public void run() { System.out.println(this.getName()+"线程启动"); System.out.println(this.getName()+"视图占用lockA"); lockA.lock(); System.out.println(this.getName()+"占用lockA成功"); try { //执行5秒业务逻辑等待其他线程占用lockB Thread.sleep(5000); System.out.println(this.getName()+"视图占用lockB"); lockB.lock(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); }finally { System.out.println(this.getName()+"线程结束"); lockA.unlock(); } } }; t1.setName("T1"); t1.start(); Thread t2 = new Thread() { @Override public void run() { System.out.println(this.getName()+"线程启动"); System.out.println(this.getName()+"视图占用lockB"); lockB.lock(); System.out.println(this.getName()+"占用lockB成功"); try { //执行5秒业务逻辑等待其他线程占用lockA Thread.sleep(5000); System.out.println(this.getName()+"视图占用lockA"); lockA.lock(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); }finally { System.out.println(this.getName()+"线程结束"); lockB.unlock(); } } }; t2.setName("T2"); t2.start(); } }
以下代码使用trylock()解决死锁问题
package lock的使用; import java.util.concurrent.TimeUnit; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; public class 死锁 { public static void main(String[] args) { Lock lockA = new ReentrantLock(); Lock lockB = new ReentrantLock(); Thread t1 = new Thread() { @Override public void run() { //判断是否占用成功的boolean值 boolean locked = false; System.out.println(this.getName()+"线程启动"); System.out.println(this.getName()+"视图占用lockA"); lockA.lock(); System.out.println(this.getName()+"占用lockA成功"); try { //执行5秒业务逻辑等待其他线程占用lockB Thread.sleep(5000); System.out.println(this.getName()+"视图占用lockB"); //下边使用trylock()在T1线程已经占用lockA的情况下去占用lockB,trylock()在规定时间占用不到的情况下会放手从而避免死锁(29行,38行) //使用trylock()占用, 给两秒抢夺资源的时间 locked = lockB.tryLock(2,TimeUnit.SECONDS); if(locked) { //如果占用成功则执行五秒的逻辑 System.out.println(this.getName()+"线程占用lockB成功"); Thread.sleep(5000); System.out.println(this.getName()+"线程占用lockB结束"); lockB.unlock(); }else { System.out.println(this.getName()+"线程花两秒时间占用lockB不成功"); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); }finally { System.out.println(this.getName()+"线程结束"); lockA.unlock(); } } }; t1.setName("T1"); t1.start(); Thread t2 = new Thread() { @Override public void run() { //判断是否占用成功的boolean值 boolean locked = false; System.out.println(this.getName()+"线程启动"); System.out.println(this.getName()+"视图占用lockB"); lockB.lock(); System.out.println(this.getName()+"占用lockB成功"); try { //执行5秒业务逻辑等待其他线程占用lockA Thread.sleep(5000); System.out.println(this.getName()+"视图占用lockA"); //下边使用trylock()在T2线程已经占用lockB的情况下去占用lockA,trylock()在规定时间占用不到的情况下会放手从而避免死锁(68行,78行) //使用trylock()占用, 给两秒抢夺资源的时间 locked = lockA.tryLock(2,TimeUnit.SECONDS); if(locked) { //如果占用成功则执行五秒的逻辑 System.out.println(this.getName()+"线程占用lockA成功"); Thread.sleep(5000); System.out.println(this.getName()+"线程占用lockA结束"); //线程结束占用 lockA.unlock(); }else { System.out.println(this.getName()+"线程花两秒时间占用lockA不成功"); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); }finally { System.out.println(this.getName()+"线程结束"); lockB.unlock(); } } }; t2.setName("T2"); t2.start(); } }