这个java程序,为什么一个notify唤醒了3个wait

来源:互联网 发布:淘宝上的男内裤买家秀 编辑:程序博客网 时间:2024/06/16 21:07

1、

public class Demo6 {public static void main(String[] args) {Go1 q = new Go1();Go2 qq = new Go2(q);Go3 qqq = new Go3(q);Come w = new Come(q);q.start();qq.start();qqq.start();w.start();}}// 线程1,打印1,等待,唤醒后打印一class Go1 extends Thread {public void run() {synchronized (this) {System.out.println("1");try {wait();} catch (Exception e) {}}System.out.println("一");}}// 线程2,打印2,等待,唤醒后打印二class Go2 extends Thread {Go1 g;Go2(Go1 g) {this.g = g;}public void run() {synchronized (g) {System.out.println("2");try {g.wait();} catch (Exception e) {}}System.out.println("二");}}// 线程3,打印3,等待,唤醒后打印三class Go3 extends Thread {Go1 g;Go3(Go1 g) {this.g = g;}public void run() {synchronized (g) {System.out.println("3");try {g.wait();} catch (Exception e) {}}System.out.println("三");}}// 唤醒线程class Come extends Thread {Go1 r;Come(Go1 r) {this.r = r;}public void run() {try {sleep(100);} catch (Exception e) {}synchronized (r) {r.notify();System.out.println("lock open");}}}

结果:

1
2
3
lock open


 

答案:

原因是共用的对象本身也是一个线程,所以notify的时候,如果被唤醒的是Go1的线程,那么Go2和Go3中的g.wait();也会跟着返回,所以相当于Go1,Go2,Go3都被唤醒,然后一起争夺锁。把共用的对象换成一个普通的对象就没有问题了。代码如下:

public class Demo7 {public static void main(String[] args) {Go g = new Go();Go1 q = new Go1(g);Go2 qq = new Go2(g);Go3 qqq = new Go3(g);Come w = new Come(g);q.start();qq.start();qqq.start();w.start();}}class Go {}class Go1 extends Thread {Go g;Go1(Go g) {this.g = g;}public void run() {synchronized (g) {System.out.println("1");try {g.wait();} catch (Exception e) {}}System.out.println("一");}}class Go2 extends Thread {Go g;Go2(Go g) {this.g = g;}public void run() {synchronized (g) {System.out.println("2");try {g.wait();} catch (Exception e) {}}System.out.println("二");}}class Go3 extends Thread {Go g;Go3(Go g) {this.g = g;}public void run() {synchronized (g) {System.out.println("3");try {g.wait();} catch (Exception e) {}}System.out.println("三");}}class Come extends Thread {Go r;Come(Go r) {this.r = r;}public void run() {try {sleep(100);} catch (Exception e) {}synchronized (r) {r.notify();System.out.println("lock open");}}}

 结果:

1
2
3
lock open

 

来源:javaeye问答

http://www.iteye.com/problems/89570

 

0 0
原创粉丝点击