我有一个 Counter 类,它将值存储为 AtomicInteger。该类应该是线程安全的。我有方法boolean consume(int number)
应该减少计数器并返回 true
如果counter >= number
,并且不应更改计数器并返回 false
如果counter < number
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赛伊:
The function should be side-effect-free, since it may be re-applied when attempted updates fail due to contention among threads.
所以,我的解决方案有副作用。使用安全吗?如果不是,我怎样才能得到相同的结果?
最佳答案
从描述来看,听起来好像您想要类似的东西:
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;
}
}
}
}
since it may be re-applied when attempted updates fail due to contention among threads.
问题中的代码可以执行一次或多次,但如果方便方法不方便,则使用这些方法无济于事。
关于应用 java AtomicIntegeraccumulateAndGet,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59126244/