【发布时间】:2021-10-23 05:37:53
【问题描述】:
我有一些代码使用synchronized 来保护我递增count++ 的计数器。
我希望我正确地保护了代码部分并因此得到2_0000_0000,因为这将是count 在多线程执行多次之后的正确值。
但是,在运行代码时,我得到的值低于预期的2_0000_0000,好像我的synchronized 没有正确保护代码部分。
为什么会这样,我做错了什么?
public class Test {
private static Integer count = 0;
private static void add10K() {
long idx = 0;
while (idx++ < 1_0000_0000) {
synchronized (count){
count += 1;
}
}
}
public static long calc() {
Thread th1 = new Thread(Test::add10K);
Thread th2 = new Thread(Test::add10K);
th1.start();
th2.start();
try {
th1.join();
th2.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
return count;
}
public static void main(String[] args) {
System.out.println(calc());
}
}
【问题讨论】:
-
您正在
count上同步。由于Integer是不可变的,因此对于每个新值来说,它都是一个新对象。 -
您锁定了一个非
final变量,这只是在要求一场灾难。只锁定final变量。创建一个专用的private static final Object lock = new Object();并在其上进行同步。 -
@Turing85:AtomicInteger 会更好,但如果使用正确,同步就足够了。
-
@JoachimSauer 确实如此。没有意识到对象发生了变化。
标签: java multithreading atomic synchronized