The thread title should be self-explnatory... I'm a bit confused between the specification of below methos from AtomicBoolean
class:
java.util.concurrent.atomic.AtomicBoolean#compareAndSet
java.util.concurrent.atomic.AtomicBoolean#getAndSet
My assemption is that both would result in the same behavior when used as a boolean clause in an if
condition:
public class Test {
private AtomicBoolean flag = AtomicBoolean(false);
public void processSomeAction() {
if (flag.getAndSet(false)) { // Shouldn't this be similar to flag.compareAndSet(false)
// process some action
}
}
//...
private void internalMutatorMethod() {
// do some staff then update the atomic flag
flas.set(true);
}
}
Assuming that I want to retrieve the current flag value and update it automaticlly, shouldn't both methods produce the same behavior?
I would much appreciate any explanations regarding how and when to use each of those if I'm missing internal differences.
compareAndSet() is an inbuilt method in java that sets the value to the passed value in the parameter if the current value is equal to the expected value which is also passed in the parameter. The function returns a boolean value which gives us an idea if the update was done or not.
AtomicBoolean class provides operations on underlying boolean value that can be read and written atomically, and also contains advanced atomic operations. AtomicBoolean supports atomic operations on underlying boolean variable. It have get and set methods that work like reads and writes on volatile variables.
Setting the AtomicBoolean's Value You can set the value of an AtomicBoolean using the set() method. Here is an example: AtomicBoolean atomicBoolean = new AtomicBoolean(true); atomicBoolean. set(false);
The documentation is pretty clear.
getAndSet
--> "Atomically sets to the given value and returns the previous value."compareAndSet
--> "Atomically sets the value to the given updated value if the current value == the expected value."Not surprisingly, compareAndSet
takes two arguments.
In your specific case:
if (flag.getAndSet(false))
will set flag
to false
only if its previous value was true
if (flag.compareAndSet(true, false))
You can look at the code for better understanding :
public final boolean getAndSet(boolean newValue) {
for (;;) {
boolean current = get();
if (compareAndSet(current, newValue))
return current;
}
}
In getAndSet
, if the value of the boolean has changed between the time you get()
the old value and the time you try to change its value, compareAndSet
won't change its value. Therefore, getAndSet
calls compareAndSet
in a loop until the boolean is set to the new value.
As to your code example :
flag.getAndSet(false)
returns the old value of the AtomicBoolean. On the other hand, flag.compareAndSet(x,false)
(note there are two arguments) returns whether the AtomicBoolean was modified, or in other words, it returns whether the old value of the AtomicBoolean was x.
When I have checked the implementation I found following
public final boolean getAndSet(boolean newValue) {
for (;;) {
boolean current = get();
if (compareAndSet(current, newValue))
return current;
}
}
Also when checking the javadoc, compareAndSet
sets value only if the comparison pass while getAndSet
simply set the value and return the previous value.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With