跟我学Java面向对象程序设计技术及应用——线程死锁技术及解决方案.docx
-
资源ID:26574157
资源大小:13.98KB
全文页数:15页
- 资源格式: DOCX
下载积分:30金币
快捷下载
![游客一键下载](/images/hot.gif)
会员登录下载
微信登录下载
三方登录下载:
微信扫一扫登录
友情提示
2、PDF文件下载后,可能会被浏览器默认打开,此种情况可以点击浏览器菜单,保存网页到桌面,就可以正常下载了。
3、本站不支持迅雷下载,请使用电脑自带的IE浏览器,或者360浏览器、谷歌浏览器下载即可。
4、本站资源下载后的文档和图纸-无水印,预览文档经过压缩,下载后原文更清晰。
5、试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。
|
跟我学Java面向对象程序设计技术及应用——线程死锁技术及解决方案.docx
跟我学Java面向对象程序设计技术及应用线程死锁技术及解决方案 1.1线程死锁技术及解决方案 1.1.1线程死锁及示例 1、为什么会产生出死锁 线程死锁时,第一个线程等待第二个线程释放资源,而同时第二个线程又在等待第一个线程释放资源。导致死锁的根源在于不适当地运用“synchronized”关键词来管理线程对特定对象的访问。 “synchronized”关键词的作用是,确保在某个时刻只有一个线程被允许执行特定的代码块,因此,被允许执行的线程首先必须拥有对变量或对象的排他性访问权。当线程访问对象时,线程会给对象加锁,而这个锁导致其它也想访问同一对象的线程被阻塞,直至第一个线程释放它加在对象上的锁。 2、线程死锁示例 (1)SomeThreadOne类代码 package com.px1987.threaddemo; public class SomeThreadOne extends Thread private Object someResourceOne =null; private Object someResourceTwo =null; public SomeThreadOne() public SomeThreadOne(Object someResourceOne,Object someResourceTwo) this.someResourceOne=someResourceOne; this.someResourceTwo=someResourceTwo; public void run() synchronized (someResourceOne) System.out.println("线程"+this.getClass().getName()+"正在锁定资源1"); try Thread.sleep(50); catch (InterruptedException e) synchronized (someResourceTwo) System.out.println("线程"+this.getClass().getName()+"正在锁定资源2"); (2)SomeThreadTwo类代码 package com.px1987.threaddemo; public class SomeThreadTwo extends Thread private Object someResourceOne =null; private Object someResourceTwo =null; public SomeThreadTwo() public SomeThreadTwo(Object someResourceOne,Object someResourceTwo) this.someResourceOne=someResourceOne; this.someResourceTwo=someResourceTwo; public void run() synchronized (someResourceTwo) System.out.println("线程"+this.getClass().getName()+"正在锁定资源2"); try Thread.sleep(50); catch (InterruptedException e) synchronized (someResourceOne) System.out.println("线程"+this.getClass().getName()+"正在锁定资源1"); (3)DeadlockTest类代码 package com.px1987.threaddemo; public class DeadlockTest public static void main(String args) final Object resource1 = "锁定资源1" final Object resource2 = "锁定资源2" Thread someThreadOne = new SomeThreadOne(resource1,resource2); someThreadOne.start(); Thread someThreadTwo = new SomeThreadTwo(resource1,resource2); someThreadTwo.start(); (4)执行的结果 该程序运行后将永远不会自己退出,除非你Ctrl+C,而且运行时CPU会直接飙到100%。 3、线程死锁示例 (1)SomeThreadOne类代码示例 package com.px1987.threaddemo; public class SomeThreadOne extends Thread private String dataOne; private String dataTwo; public SomeThreadOne() public SomeThreadOne(String dataOne,String dataTwo) this.dataOne=dataOne; this.dataTwo=dataTwo; public void run() /* *同步中又有同步,就可能死锁 */ synchronized(dataOne) System.out.println(Thread.currentThread().getName()+"锁定dataOne"); try Thread.sleep(1000); catch (InterruptedException e) e.printStackTrace(); synchronized(dataTwo) System.out.println(Thread.currentThread().getName()+"锁定dataTwo"); (2)SomeThreadTwo类代码 package com.px1987.threaddemo; public class SomeThreadTwo extends Thread private String dataOne; private String dataTwo; public SomeThreadTwo() public SomeThreadTwo(String dataOne,String dataTwo) this.dataOne=dataOne; this.dataTwo=dataTwo; public void run() /* *同步中又有同步,就可能死锁 */ synchronized(dataTwo) System.out.println(Thread.currentThread().getName()+"锁定dataTwo"); try Thread.sleep(1000); catch (InterruptedException e) e.printStackTrace(); synchronized(dataOne) System.out.println(Thread.currentThread().getName()+"锁定dataOne"); (3)ThreadDeadLockDemo类代码 package com.px1987.threaddemo; public class ThreadDeadLockDemo public ThreadDeadLockDemo() public static void main(String args) /* * 定义线程中所需要的资源 */ String someDataToDataOne="这是给线程一中的dataOne的赋值" String someDataToDataTwo="这是给线程二中的dataTwo的赋值" /* * 创建出2个不同的线程 */ SomeThreadOne threadOneObj=new SomeThreadOne(someDataToDataOne,someDataToDataTwo); SomeThreadTwo threadTwoObj=new SomeThreadTwo(someDataToDataOne,someDataToDataTwo); /* * 分别启动两个线程 */ threadOneObj.start(); threadTwoObj.start(); (4)执行的结果 4、不正确的线程同步而造成的线程死锁示例 (1)PushDataThread类的代码示例 package com.px1987.threaddemo; public class PushDataThread extends Thread private SynchronizedStack synchronizedStack=null; public PushDataThread(SynchronizedStack synchronizedStack) this.synchronizedStack=synchronizedStack; Override public void run() for(int loopIndex = 0; loopIndex < 100; loopIndex+) try Thread.sleep(10); catch (InterruptedException e) e.printStackTrace(); synchronizedStack.pushSomeOneData(new Integer(loopIndex).toString(); (2)PopDataThread类的代码示例 package com.px1987.threaddemo; public class PopDataThread extends Thread private SynchronizedStack synchronizedStack=null; public PopDataThread(SynchronizedStack synchronizedStack) this.synchronizedStack=synchronizedStack; Override public void run() for(int loopIndex = 0; loopIndex < 100; loopIndex+) try System.out.println(synchronizedStack.popSomeOneData(); catch (Exception e) e.printStackTrace(); (3)SynchronizedStack类的代码示例 package com.px1987.threaddemo; import java.util.LinkedList; public class SynchronizedStack private LinkedList allDataList = new LinkedList(); /* *保存数据的方法 */ public synchronized void pushSomeOneData(Object someOneData) System.out.println("开始压栈:" + someOneData); synchronized (allDataList) allDataList.addLast(someOneData); notify(); System.out.println("结束压栈:" + someOneData); /* *恢复数据的方法 */ public synchronized Object popSomeOneData() throws Exception System.out.println("开始弹栈"); synchronized (allDataList) if (allDataList.size() <= 0) wait(); return allDataList.removeLast(); 注意同步方法中又出现同步代码段。 (4)TestSynchronizedStack类的代码示例 该程序构造了一个模拟的Stack,并启动了两个线程分别操作该Stack。一个线程向Stack 中添加数据,另外一个线程从Stack 中取出数据并打印。 package com.px1987.threaddemo; public class TestSynchronizedStack public static void main(String args) final SynchronizedStack stack = new SynchronizedStack(); new PushDataThread(stack).start(); new PopDataThread(stack).start(); (5)执行的结果 运行程序后就会发现程序输出相关的信息后,再也没有后续输出了产生了死锁。 5、改进的代码示例 (1)SynchronizedStack类的代码示例 package com.px1987.threaddemo; import java.util.LinkedList; public class SynchronizedStack private LinkedList allDataList = new LinkedList(); /* *保存数据的方法 */ public synchronized void pushSomeOneData(Object someOneData) System.out.println("开始压栈:" + someOneData); allDataList.addLast(someOneData); notify(); System.out.println("结束压栈:" + someOneData); /* *恢复数据的方法 */ public synchronized Object popSomeOneData() throws Exception System.out.println("开始弹栈"); if (allDataList.size() <= 0) wait(); return allDataList.removeLast(); (2)执行的结果