AtomicInteger and Compare operations

V1666 :

I'm trying to use an AtomicInteger variable as lock. So, wondering if the code posted below is thread safe. I know incrementAndGet() is an atomic operation. But, I'm not sure if the subsequent '==' operation will be atomic as well (what if the value gets incremented to 2, by the time I make the comparison.). So posting this question to hear your thoughts.

private AtomicInteger count = new AtomicInteger(0); //Shared variable
private final int max = 1;

if(count.incrementAndGet() == max) {
  //Do something
}
steffen :

Since incrementAndGet() is an atomic operation, at most one thread will get 1 for result (as long as the AtomicInteger is not set to a value lower than 1). This is guaranteed by AtomicInteger. Although the actual comparison is not part of this atomic operation, only the thread which received 1 will run into the if block. That's because the comparison compares two values of type int: the result of incrementAndGet()) and max. The AtomicInteger doesn't play a role in it since the primitive int doesn't change it's value when the inner state of count changes. tl;dr: Your code is equivalent to:

final int val = count.incrementAndGet(); // (it makes no difference if val is not 'final`)
if (val == max) {
    // ...
}

Java provides many other ways to achieve thread-safety (Lock, CountDownLatch, Semaphore, ...), but since you are referring to an AtomicInteger, I believe AtomicInteger.compareAndSet() is more accurate to what you were asking:

if (count.compareAndSet(0, 1)) {
    // executed if count == 0
    count.set(0);
}

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=103252&siteId=1