[英]why does deadlock not happen
死锁描述了由于永远等待而又阻塞了两个线程的情况。 当发生死锁时,程序将永远挂起,您唯一能做的就是杀死该程序。
为什么在下面给出的示例生产者消费者问题中不会发生死锁:
我不知道为什么当同步对象正在等待其他线程释放锁时,同步块中的调用wait方法不会导致死锁?
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
public class WaitAndNotify {
public static void main(String[] args) {
List<Integer> list = new ArrayList<>();
var th1 = new Thread(new Producer(list));
var th2 = new Thread(new Consumer(list));
th1.start();
th2.start();
}
}
class Producer implements Runnable {
private List<Integer> list;
private final Integer MAX_SIZE_LIST = 5;
public Producer(List<Integer> list) {
this.list = list;
}
@Override
public void run() {
Random rand = new Random();
for (;;) {
synchronized (this.list) {
if (list.size() == MAX_SIZE_LIST) { // check list is full or not
try {
System.out.println("list full wait producer");
list.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
var randNumber = rand.nextInt();
System.out.println("produce number => " + randNumber);
list.add(randNumber);
list.notify();
}
}
}
}
class Consumer implements Runnable {
private List<Integer> list;
public Consumer(List<Integer> list) {
this.list = list;
}
@Override
public void run() {
for (;;) {
synchronized (this.list) {
if (list.size() == 0) {
try {
System.out.println("list empty consumer wait");
list.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println("consume number <= " + list.remove(0));
list.notify();
}
}
}
}
您可能会认为, Consumer
将在list.wait()
处list.wait()
而Producer将在list.wait()
synchronized (this.list)
处阻塞。
它起作用,因为list.wait()
释放了synchronized
块内list
的所有权。 wait
返回后,线程再次获取所有权。
正如我们已经在这里讨论的那样,由于使用了synchronized block, list.wait() and list.notify()
方法synchronized block, list.wait() and list.notify()
因此没有发生死锁。
这是一个死锁的好例子: https : //docs.oracle.com/javase/tutorial/essential/concurrency/deadlock.html
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.