产生死锁的条件:

1.有至少一个资源不能共享
2.至少有一个任务必须持有一个资源并且等待获取另一个被别的任务持有的资源
3.资源不能任务抢占
4.必须有循环等待

只要打破其中一个条件就不会产生死锁,通常是打破第4个条件

package DeadLock;

public class Chopstick {
private boolean taken = false; public synchronized void take() throws InterruptedException {
while (taken) {
wait();
}
taken = true;
} public synchronized void drop() {
taken = false;
notifyAll();
}
}
package DeadLock;

import java.util.Random;
import java.util.concurrent.TimeUnit; public class Philosopher implements Runnable { private Chopstick left;
private Chopstick right;
private final int id;
private final int ponderFactor;
private Random rand = new Random(47); private void pause() throws InterruptedException {
if (ponderFactor == 0)
return; //赞同随机毫秒数
TimeUnit.MILLISECONDS.sleep(rand.nextInt(ponderFactor * 250));
} public Philosopher(Chopstick left, Chopstick right, int ident, int ponder) {
this.left = left;
this.right = right;
id = ident;
ponderFactor = ponder;
} @Override
public void run() {
try {
while (!Thread.interrupted()) {
System.out.println(this + " " + "thinking");
pause();
// Philosopher becomes hungry
System.out.println(this + " " + " grabbing right");
right.take();
System.out.println(this + " " + "grabbing left");
left.take();
System.out.println(this + " " + "eating");
pause();
right.drop();
left.drop();
}
} catch (InterruptedException e) {
System.out.println(this + " " + "exiting via interrupt");
}
} public String toString() {
return "Philosopher " + id;
} }

造成死锁

package DeadLock;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit; public class DeadlockingDiningPhilosophers {
public static void main(String[] args) throws Exception {
int ponder = 5;
if (args.length > 0)
ponder = Integer.parseInt(args[0]); int size = 5;
if (args.length > 1)
size = Integer.parseInt(args[1]); ExecutorService exec = Executors.newCachedThreadPool();
Chopstick[] sticks = new Chopstick[size];
for (int i = 0; i < size; i++) {
exec.execute(new Philosopher(sticks[i], sticks[(i + 1) % size], i,
ponder));
}
if (args.length == 3 && args[2].equals("timeout"))
TimeUnit.SECONDS.sleep(5);
else {
System.out.println("Press'Enter' to quit");
System.in.read();
}
exec.shutdownNow();
}
}

避免死锁

package DeadLock;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit; import javax.print.attribute.Size2DSyntax; public class FixedDiningPhilosophers {
public static void main(String[] args) throws Exception{
int ponder=5;
if(args.length>0)
ponder=Integer.parseInt(args[0]); int size=5;
if(args.length>1)
size=Integer.parseInt(args[1]);
ExecutorService exec=Executors.newCachedThreadPool();
Chopstick[] sticks=new Chopstick[size];
for (int i = 0; i < size; i++) {
sticks[i]=new Chopstick();
}
for (int i = 0; i < size; i++) {
if(i<(size-1))
exec.execute(new Philosopher(sticks[i],sticks[i+1], i, ponder));
else
exec.execute(new Philosopher(sticks[0], sticks[i], i, ponder));
}
if(args.length==3&&args[2].equals("timeout"))
TimeUnit.SECONDS.sleep(5);
else{
System.out.println("Press 'Enter' to quit");
System.in.read();
}
exec.shutdownNow();
}
}

java多线程之死锁的更多相关文章

  1. Java多线程和死锁

    一 .多线程: 售票窗口简单实例: public class SaleTicket { public static class Sale implements Runnable{ ; // @Over ...

  2. Java多线程:死锁

    周末看到一个用jstack查看死锁的例子.昨天晚上总结了一下jstack(查看线程).jmap(查看内存)和jstat(性能分析)命令.供大家参考  1.Jstack 1.1 jstack能得到运行j ...

  3. JAVA多线程----用--死锁

    (1) 互斥条件:一个资源每次只能被一个进程使用.(2) 请求与保持条件:一个进程因请求资源而阻塞时,对已获得的资源保持不放.(3) 不剥夺条件:进程已获得的资源,在末使用完之前,不能强行剥夺.(4) ...

  4. Java多线程:线程死锁

    发生死锁的原因通常是两个对象的锁相互等待造成的. 以下用一个实例来构造这样的情况: package basic.e_deadlock; import org.apache.log4j.Logger; ...

  5. java多线程(死锁,lock接口,等待唤醒机制)

    一.Lock接口 常用方法 Lock提供了一个更加面对对象的锁,在该锁中提供了更多的操作锁的功能. 使用Lock接口,以及其中的lock()方法和unlock()方法替代同步,对电影院卖票案例中Tic ...

  6. Java多线程学习——死锁的一个容易理解的例子

    发生死锁的情况:多个线程需要同时占用多个共享资源而发生需要互相死循环等待的情况 public class Mirror { //镜子 } public class Lipstick { //口红 } ...

  7. Java 多线程:锁(一)

    Java 多线程:锁(一) 作者:Grey 原文地址: 博客园:Java 多线程:锁(一) CSDN:Java 多线程:锁(一) CAS 比较与交换的意思 举个例子,内存有个值是 3,如果用 Java ...

  8. Java多线程中的死锁问题

    Java程序基本都要涉及到多线程,而在多线程环境中不可避免的要遇到线程死锁的问题.Java不像数据库那么能够检测到死锁,然后进行处理,Java中的死锁问题,只能通过程序员自己写代码时避免引入死锁的可能 ...

  9. Java多线程7:死锁

    前言 死锁单独写一篇文章是因为这是一个很严重的.必须要引起重视的问题.这不是夸大死锁的风险,尽管锁被持有的时间通常很短,但是作为商业产品的应用程序每天可能要执行数十亿次获取锁->释放锁的操作,只 ...

随机推荐

  1. sed命令拷屏

    http://blog.sina.com.cn/s/blog_45497dfa0100w6r3.html  sed样例较多,可以参考 http://blog.sina.com.cn/s/blog_6d ...

  2. ASP.NET Cookie 概述【转】

    来源:http://msdn.microsoft.com/zh-cn/library/ms178194(VS.80).aspx ASP.NET Cookie 概述 Cookie 提供了一种在 Web ...

  3. iOS开发笔记-swift实现iOS数据持久化之归档NSKeyedArchiver

    IOS数据持久化的方式分为三种: 属性列表 (plist.NSUserDefaults) 归档 (NSKeyedArchiver) 数据库 (SQLite.Core Data.第三方类库等 归档(又名 ...

  4. Oracle查找表的外键引用关系

    Oracle查找表的外键引用关系 select t1.table_name, t2.table_name as "TABLE_NAME(R)", t1.constraint_nam ...

  5. java 金额计算,商业计算 double不精确问题 BigDecimal,Double保留两位小数方法

    解决办法================== http://blog.javaxxz.com/?p=763 一提到Java里面的商业计算,我们都知道不能用float和double,因为他们无法 进行精 ...

  6. Oracle自增主键的添加[sequence]--表数据已存在

    --增加主键ID ); --设置sequence使ID自增 create sequence SEQ_ID minvalue maxvalue start ; --将id的值设置为sequence Up ...

  7. mysql命令行导入sql文件

    今天从windows上导出一个sql执行文件,再倒入到unbutn中,结果出现乱码,折腾7-8分钟, 解决方式 在导出mysql sql执行文件的时候,指定一下编码格式: 复制代码代码如下: mysq ...

  8. JABX简单介绍

    主要引至http://suo.iteye.com/blog/1233458 一.简介 1.概念是什么:(Java Architecture for XML Binding) 是一个业界的标准,是一项可 ...

  9. 关于SqlServer的DBHelper类以及数据分页

    前端: <My:AspNetPager class="arPage" PageSize="20" UrlPaging="true" r ...

  10. 【linux】bash常用快捷键

    Ctrl + r:逆向搜索命令历史 Ctrl + l:清屏 Ctrl + c:终止命令 Ctrl + u:删除光标前的指令 Ctrl + k:删除光标后的指令 Ctrl + d:退出登陆