Wait until boolean value changes it state

JavaMultithreadingBoolean

Java Problem Overview


I have a thread which wait for a boolean value to change like this:

while(!value)
{
  Thread.sleep(1000)
}
// Do some work after change of the value

This is not my prefered way to do this, cause of massive CPU consumption.

Is there any way to block the Thread, until the boolean value changes it state?

Java Solutions


Solution 1 - Java

> This is not my prefered way to do this, cause of massive CPU consumption.

If that is actually your working code, then just keep it like that. Checking a boolean once a second causes NO measurable CPU load. None whatsoever.

The real problem is that the thread that checks the value may not see a change that has happened for an arbitrarily long time due to caching. To ensure that the value is always synchronized between threads, you need to put the volatile keyword in the variable definition, i.e.

private volatile boolean value;

Note that putting the access in a synchronized block, such as when using the notification-based solution described in other answers, will have the same effect.

Solution 2 - Java

You need a mechanism which avoids busy-waiting. The old wait/notify mechanism is fraught with pitfalls so prefer something from the java.util.concurrent library, for example the CountDownLatch:

public final CountDownLatch latch = new CountDownLatch(1);

public void run () {
  latch.await();
  ...
}

And at the other side call

yourRunnableObj.latch.countDown();

However, starting a thread to do nothing but wait until it is needed is still not the best way to go. You could also employ an ExecutorService to which you submit as a task the work which must be done when the condition is met.

Solution 3 - Java

How about wait-notify

private Boolean bool = true;
private final Object lock = new Object();

private Boolean getChange(){
  synchronized(lock){
    while (bool) {
      bool.wait();
    }
   }
  return bool;
}
public void setChange(){
   synchronized(lock){
       bool = false;
       bool.notify();
   }
}

Solution 4 - Java

Ok maybe this one should solve your problem. Note that each time you make a change you call the change() method that releases the wait.

Integer any = new Integer(0);

public synchronized boolean waitTillChange() {
    any.wait();
    return true;
}

public synchronized void change() {
    any.notify();
}

Solution 5 - Java

I prefer to use mutex mechanism in such cases, but if you really want to use boolean, then you should declare it as volatile (to provide the change visibility across threads) and just run the body-less cycle with that boolean as a condition :

//.....some class

volatile boolean someBoolean; 

Thread someThread = new Thread() {

    @Override 
    public void run() {
        //some actions
        while (!someBoolean); //wait for condition 
        //some actions 
    }
    
};

Solution 6 - Java

public Boolean test() throws InterruptedException {
    BlockingQueue<Boolean> booleanHolder = new LinkedBlockingQueue<>();
    new Thread(() -> {
        try {
            TimeUnit.SECONDS.sleep(2);
            booleanHolder.put(true);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }).start();
    return booleanHolder.poll(4, TimeUnit.SECONDS);
}

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionMarcelView Question on Stackoverflow
Solution 1 - JavaMichael BorgwardtView Answer on Stackoverflow
Solution 2 - JavaMarko TopolnikView Answer on Stackoverflow
Solution 3 - JavaSubhrajyoti MajumderView Answer on Stackoverflow
Solution 4 - Javaluiso1979View Answer on Stackoverflow
Solution 5 - Javauser2813148View Answer on Stackoverflow
Solution 6 - JavakrekerView Answer on Stackoverflow