当多个线程访问同一个实例变量时,往往会出现脏数据。下面举一个例子:
为了对比,首先我们先写一个SynchronizedTest类,包含一个不加锁的方法test
package testwebapp;
public class SynchronizedTest {
private int num;
public void test(String type){
if("1".equals(type)){
num = 1;
System.out.println("======num = 1=====");
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}else{
num = 2;
System.out.println("======num = 2=====");
}
System.out.println("The num is:"+num);
}
}
接下来,写两个类TestOne和TestTwo分别继承Thread类,然后调用SynchronizedTest的test方法
package testwebapp;
public class TestOne extends Thread {
private SynchronizedTest synchronizedTest;
public TestOne(SynchronizedTest synchronizedTest){
this.synchronizedTest = synchronizedTest;
}
public void run(){
synchronizedTest.test("1");
}
}
package testwebapp;
public class TestTwo extends Thread {
private SynchronizedTest synchronizedTest;
public TestTwo(SynchronizedTest synchronizedTest){
this.synchronizedTest = synchronizedTest;
}
public void run(){
synchronizedTest.test("2");
}
}
最后,写一个测试类Test,实例化TestOne和TestTwo启动线程
package testwebapp;
public class Test {
public static void main(String[] args) {
SynchronizedTest st = new SynchronizedTest();
TestOne to = new TestOne(st);
TestTwo tt = new TestTwo(st);
to.start();
tt.start();
}
}
运行结果如下:
======num = 1=====
======num = 2=====
The num is:2
The num is:2
这显然和我们预期的结果:
======num = 1=====
The num is:1
======num = 2=====
The num is:2
不符合
执行顺序不一致时因为我们使用了多线程,那为什么输出结果都是2呢?应该怎样解决?
线程不安全导致了输出结果都是2,我们可以使用对象锁synchronized来解决这个问题,代码如下:
package testwebapp;
public class SynchronizedTest {
private int num;
//此处加上synchronized就和我们预期结果一致了
public synchronized void test(String type){
if("1".equals(type)){
num = 1;
System.out.println("======num = 1=====");
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}else{
num = 2;
System.out.println("======num = 2=====");
}
System.out.println("The num is:"+num);
}
}
输出结果:
======num = 1=====
The num is:1
======num = 2=====
The num is:2