class Containers{

int index = 1;

public synchronized void put() {          //................1.
                  index++;
if(index == 3) {
try {
this.wait();  //....................2.
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println("put-wait");        //.............. 3.
this.notify();                        //..................4.
System.out.println("put-notify后面的内容");  // ............5.
}

public synchronized void get() {
                  index--;
if(index == 1) {
try {
System.out.println("g.");
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
this.notify();        //如果这个地方notify以后,上面的put方法是从什么地方开始执行 ......6.
}
}
-------------------------------------------------------
程序中启动了两个线程,并且都用的一个上面类的实例。用的 是一个对象
假如put方法里面的wait方法执行了,这个时候就要执行get方法了
然后get方法调用notify方法后。put方法接着是从什么地方执行呢?
请高手分析一下。

解决方案 »

  1.   

    唤醒调用put()方法的线程,该线程在重新获得Containers对象锁之后从3地方开始执行
      

  2.   

    总之是从wait()后的下一行代码开始执行。
    代码稍作修改,更加直观些。public class Containers { int index = 1; public synchronized void put() { //................1.
    index++;
    if (index == 3) {
    try {
    System.out.println("put wait...");
    this.wait(); //....................2.
    System.out.println("put  restart ! ..........3"); //.............. 3.
    } catch (InterruptedException e) {
    e.printStackTrace();
    }
    }
    this.notify(); //..................4.
    } public synchronized void get() {
    index--;
    if (index == 1) {
    try {
    this.wait();
    } catch (InterruptedException e) {
    e.printStackTrace();
    }
    }
    System.out.println("get notify --------");
    this.notify(); //如果这个地方notify以后,上面的put方法是从什么地方开始执行 ......6.
    }

    public static void main(String[] args) {
    final Containers c = new Containers();
    new Thread() {
    public void run() {
    for (int i = 0; i < 10; i++) {
    c.put();
    }
    }
    }.start();

    new Thread() {
    public void run() {
    for (int i = 0; i < 10; i++) {
    c.get();
    }
    }
    }.start();
    }
    }其中一次的执行结果如下:
    put wait...
    get notify --------
    put  restart ! ..........3
    put wait...
    get notify --------
    get notify --------
    put  restart ! ..........3
    get notify --------
    put wait...
    get notify --------
    put  restart ! ..........3
    put wait...
    get notify --------
    get notify --------
    put  restart ! ..........3
    put wait...
    get notify --------
    get notify --------
    put  restart ! ..........3
    get notify --------
    从结果看出"get notify --------"之后,put总是从"put  restart ! ..........3"开始执行。
      

  3.   

    楼上两位给说对了一半。情况1:
    index=2 -> 进入put() -> index++ -> index=3 -> this.wait() -> 进入get() -> index-- 
    -> index=2 -> this.notify() -> 走出get() -> 程序从3开始执行。情况2:
    index=1 -> 进入get() -> index-- -> index=0 -> this.notify() -> 走出get() -> 程序从1开始执行。情况3:
    index=2 -> 进入get() -> index-- -> index=1 -> this.wait() -> 程序从1开始执行。
      

  4.   

    明白了!谢谢大家。
    那我还有一个疑问???
    那就是如果,代码如下:this.notify();   //...........1
    system.out.println(".....");  //..............2如果当前线程调用了1处的notify()方法后,是直接放弃执行2呢? 还是把当前的方法的内容执行完,然后再让其他线程执行,如果这样,可不可以说,调用了notify()只是让其他线程成准备状态,并没有立即执行
    那如果是下面的形式呢? 又会如何this.notify();   //...........1
    while(true) {
    System.out.println("zhixing");
    }//..............2
      

  5.   

    这个问题其实上面的情况1已经回答了:情况1: 
    index=2 -> 进入put() -> index++ -> index=3 -> this.wait() -> 进入get() -> index-- 
    -> index=2 -> this.notify() -> 走出get() -> 程序从3开始执行。 从以上例子可以看出: 必须走出get(),程序才会从3开始执行。那是因为synchronized的缘故。