问题描述
假设有以下两个计数器实现:
Suppose two following counter implementations:
class Counter {
private final AtomicInteger atomic = new AtomicInteger(0);
private int i = 0;
public void incrementAtomic() {
atomic.incrementAndGet();
}
public synchronized void increment() {
i++;
}
}
乍一看,原子应该更快,更具可扩展性。我相信他们是。但它们是否比 synchronized
阻止所有时间更快?或者这个规则被破坏时存在某些情况(例如SMP /单CPU机器,不同的CPU ISA,操作系统等)?
At first glance atomics should be faster and more scalable. And they are, I believe. But are they faster than synchronized
blocks all the time? Or some situations exists when this rule is broken (e.g. SMP/Single CPU machine, different CPU ISA, OS'es etc.)?
推荐答案
incrementAndGet
可以作为CAS循环实现。在高度满足的情况下,导致 n -1的线程无法导致O( n )问题, n 线程。
incrementAndGet
may well be implemented as a CAS-loop. In highly contented situations that can result in n-1 of your threads failing leading to an O(n) problem, for n threads.
(对于@Geek:
通常 getAndIncrement
可能实现如下:
int old;
do {
old = value;
} while (!compareAndSet(value, old, old+1));
return old;
想象一下,你有一个 n 线程在同一个原子上执行这个代码,它们碰巧彼此同步。第一次迭代 kn 工作。只有一个CAS将成功。其他 n -1个线程将重复练习,直到只剩下一个。所以总工作量为O( n ^ 2)(最差情况)而不是O( n )。)
Imagine you have a n threads executing this code on the same atomic, and they happen to be in step with each other. The first iteration does kn work. Only one CAS will succeed. The other n-1 threads will repeat the exercise until there is only one left. So the total work is O(n^2) (worst case) instead of O(n). )
话虽如此,获得一个锁将需要做类似的事情,并且锁定不是'在极度争辩时达到最佳状态。在使用需要在get和compareAndSwap之前进行大量计算的CAS循环之前,您不太可能看到锁的优势。
Having said that, acquiring a lock will need to do something similar at best, and locks aren't at their best when heavily contended. You're not likely to see much of an advantage for locks until you use a CAS-loop which requires significant computation before get and compareAndSwap.
这篇关于同步块可以比Atomics更快吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!