
[英]Is there any functional difference between AtomicInteger.updateAndGet() and AtomicInteger.accumulateAndGet()?
[英]java AtomicInteger accumulateAndGet is applied
我有一个将值存储为 AtomicInteger 的 Counter 类。 该类应该是线程安全的。 我有方法boolean consume(int number)
如果counter >= number
应该递减计数器并返回true
,如果counter < number
则不应该更改计数器并返回false
class Counter {
AtomicInteger counter = new AtomicInteger(initialValue);
boolean consume(int number) {
counter.accumulateAndGet(number, (prev, next) -> {
if (number <= prev) {
return prev - number;
} else {
// not modify the previous number;
return prev;
}
});
return ???
}
}
而且我不知道该功能是否适用。 我找到了以下解决方案
boolean consume(int number) {
AtomicBoolean result = new AtomicBoolean(false);
counter.accumulateAndGet(number, (prev, next) -> {
if (number <= prev) {
result.set(true);
return prev - number;
// function applied
} else {
result.set(false);
// not modify the previous number;
return prev;
}
});
return result.get();
}
但是accumulateAndGet
的 javadoc 说:
该函数应该是无副作用的,因为当由于线程之间的争用而尝试更新失败时,它可能会被重新应用。
所以,我的解决方案有副作用。 使用安全吗? 如果不是,我怎样才能得到相同的结果?
从描述中,听起来好像你想要这样的东西:
class Counter {
private final int initialValue = 42; // make compile
/** Non-negative count. */
private final AtomicInteger counter = new AtomicInteger(initialValue);
public boolean consume(int number) {
for (;;) {
int old = counter.get();
int next = old-number;
if (next >= 0) {
if (counter.compareAndSet(old, next)) {
return true;
};
} else {
return false;
}
}
}
}
因为当由于线程之间的争用而尝试更新失败时,它可能会被重新应用。
问题中的代码可以执行一次或多次,但如果不方便,使用便利方法无济于事。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.