假设你有以下课程
public class AccessStatistics {
private final int noPages, noErrors;
public AccessStatistics(int noPages, int noErrors) {
this.noPages = noPages;
this.noErrors = noErrors;
}
public int getNoPages() { return noPages; }
public int getNoErrors() { return noErrors; }
}然后执行以下代码
private AtomicReference<AccessStatistics> stats =
new AtomicReference<AccessStatistics>(new AccessStatistics(0, 0));
public void incrementPageCount(boolean wasError) {
AccessStatistics prev, newValue;
do {
prev = stats.get();
int noPages = prev.getNoPages() + 1;
int noErrors = prev.getNoErrors;
if (wasError) {
noErrors++;
}
newValue = new AccessStatistics(noPages, noErrors);
} while (!stats.compareAndSet(prev, newValue));
}在最后一行while (!stats.compareAndSet(prev, newValue))中,compareAndSet方法如何确定prev和newValue之间的相等?实现AccessStatistics方法是否需要equals()类?如果没有,为什么?javadoc为AtomicReference.compareAndSet声明了以下内容
如果当前值==为期望值,则
原子地将值设置为给定的更新值。
..。但这一断言似乎非常普遍,我在AtomicReference上读过的教程从来没有建议为包装在AtomicReference中的类实现相等()。
如果包装在AtomicReference中的类需要实现相等(),那么对于比AccessStatistics更复杂的对象,我想同步更新对象而不使用AtomicReference的方法可能更快。
发布于 2009-12-08 21:33:01
它像使用了==运算符一样比较了refrerences。这意味着引用必须指向同一个实例。不使用Object.equals()。
发布于 2011-12-12 14:03:42
实际上,它没有比较prev和newValue!
相反,它将存储在stats中的值与prev进行比较,并且只有在它们相同的情况下,它才会将存储在stats中的值更新为newValue。如前所述,它使用相等运算符(==)来完成此操作。这意味着,当prev指向存储在stats中的相同对象时,将更新stats。
发布于 2009-12-08 21:31:57
它只检查对象引用相等(又名==),因此如果AtomicReference持有的对象引用在获得引用后发生了更改,则不会更改引用,因此必须重新开始。
https://stackoverflow.com/questions/1869959
复制相似问题