日期:2014-05-20  浏览次数:20633 次

一个关于线程同步的基础问题
先贴代码: 
public class WaitTest {

public final static Object o = "abc";
  


 public static void main(String[] args) {
     test3();
  }
 public static void test3(){
     ThreadB b = new ThreadB();
    
     b.start();
    
        synchronized (o) {
            try {
                System.out.println("Waiting for b to complete...");
                o.wait();
            } catch (Exception e) {
                e.printStackTrace();
            }
            System.out.println("Total is: " + b.total);       
        }      
    }
}
class ThreadB extends Thread {
    int total = 0;
     
    public void run() {
        synchronized (WaitTest.o) {
            System.out.println("ThreadB");
            for (int i = 0; i < 50; i++) {
                total += i;
                try {
                    Thread.sleep(100);
                    System.out.print(i);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }                          
            }
            System.out.println();
            WaitTest.o.notify();
        }
    }  
}


执行的结果是:先输出了Waiting for b to complete...

然后输出了 ThreadB 与50个数字

最后输出了Total is: 1225

按照我的理解,如果先输出了Waiting for b to complete...,那么意味着对象o已经被同步了,任何被此对象同步的方法都是无法执行的。为什么下面还能接着执行run()方法。


代码的顺序调整下就可以得出上面的结论

 public static void test3(){
     ThreadB b = new ThreadB();
    
        synchronized (o) {
            try {
                System.out.println("Waiting for b to complete...");
                o.wait();
            } catch (Exception e) {
                e.printStackTrace();
            }
            System.out.println("Total is: " + b.total);       
        }  
        
        b.start();
    }


求大神来解答下。
------解决方案--------------------

public static void test3(){
        ThreadB b = new ThreadB();
         
        b.start();
         
        synchronized (o) {//主线程获取o上的锁
            try {
                System.out.println("Waiting for b to complete...");