关于线程同步的问题

来源:百度知道 编辑:UC知道 时间:2024/06/11 16:43:53
哪位大虾能详细的给我讲讲下面对段代码为什么输出结果会是1000而不是2000喃?m1这个方法首先把b的值改成了1000了然后开始睡5秒 接着m2先睡2.5秒把b的值给改成了2000 那么打印结果因该为2000才对
package com.bjsxt.yewei;

public class TT implements Runnable {
int b = 100;

public synchronized void m1() throws Exception{
//Thread.sleep(2000);
b = 1000;
Thread.sleep(5000);
System.out.println("b = " + b);
}

public synchronized void m2() throws Exception {
Thread.sleep(2500);
b = 2000;
}

public void run() {
try {
m1();
} catch(Exception e) {
e.printStackTrace();
}
}

public static void main(String[] args) throws Exception {
TT tt = new TT();
Thread t = new Thread(tt);
t.start();

tt.m2();
System.out.println(tt.b);
}
}
main函数中的t.start(); 的下面的位置加上Thread.sleep(5000);让main线程先去睡眠,这样应该就能保证结果是2000了! 这还是不行 还是输出结果为1000

因为有synchronized关键字,所以两个线程执行的方法m1,m2肯定是串行的,这就是说只是看哪个方法先执行了,一个方法先执行就意味着另一个方法肯定是在前面的方法完毕还才开始执行。你在t.start(); 的下面的位置加上Thread.sleep(5000);这样t肯定会先执行m1。因为synchronized的原因main线程的m2会在m1完毕后再执行,所以结果会是
b = 1000
2000
而原程序中(没有加Thread.sleep(5000)),线程t和线程main谁先运行自己的方法是取决于当时的运行情况的,而因为t.start()需要建立新的线程,要消耗更多的系统时间,后执行的可能性大,所以原程序结果为1000的可能性大(也就是m2先执行):
2000
b = 1000

我个人认为,“b = 2000”这个行是永远不会被输出的

在我的机器上输出的结果先是2000. 

程序中有两个不是守护线程的线程,也就是main和t。 

由于是main先执行tt.m2()和t.start()先执行的几率问题。都是不存在确定性的。最好的办法是在main函数中的t.start(); 的下面的位置加上Thread.sleep(5000);让main线程先去睡眠,这样应该就能保证最后一行的结果是2000了!