简体   繁体   中英

Java infinite loop performance

I have a Thread that only has to work when a certain circumstance comes in. Otherwise it just iterates over an empty infinite loop:

public void run() {
    while(true) {
        if(ball != null) {
             // do some Calculations
        }
    }
}

Does it affect the performance when the loop actually does nothing but it has to check if it has to do the calculation every iteration? Only creating a this Thread when needed is not an option for me, because my class which implements Runnable is a visual object which has be shown all the time.

edit : so is the following a good solution? Or is it better to use a different method (concerning performance)?

private final Object standBy = new Object();

public void run() {
    while(true) {
        synchronized (standBy) {
            while(ball != null)  // should I use while or if here?
                try{ standBy.wait() }
                catch (InterruptedException ie) {}
        }
        if(ball != null) {
             // do some Calculations
        }
}

public void handleCollision(Ball b) {
    // some more code..
    ball = b;
    synchronized (standBy) {
        standBy.notify();
    }
}

You might want to consider putting the thread to sleep and only waking it up only when your 'ball' variable becomes true. There are multiple ways of doing this, from using the very low level, wait and notify statements to using the java.util.concurrent classes which provide a less error prone way of doing this. Have a look at the documentation for the condition interface. A data structure like a BlockingQueue would also be a solution.

Yes it does. This is the most simple implementation of busy waiting , and should be avoided whenever possible. Use wait/notify or java.util.concurrent mechanisms. Maybe you should be more specific about what exactly you want to achieve to get more useful responses.

Yes, it will certainly affect performance. To increase performance, you can consider putting in a bit of a time delay (say 500ms or 1000ms or even higher) in your code depending how crucial timing is to you.

Share a BlockingQueue between your threads.

 class Producer implements Runnable {
   private final BlockingQueue queue;
   Producer(BlockingQueue q) { queue = q; }
   public void run() {
     try {
       while (true) { queue.put(produce()); }
     } catch (InterruptedException ex) { ... handle ...}
   }
   Object produce() { ... }
 }

 class Consumer implements Runnable {
   private final BlockingQueue queue;
   Consumer(BlockingQueue q) { queue = q; }
   public void run() {
     try {
       while (true) { consume(queue.take()); }
     } catch (InterruptedException ex) { ... handle ...}
   }
   void consume(Object x) { ... }
 }

I found the following interesting thing. In task manager, running that infinite loop like that, would consume 17% of my CPU. Now, if I added a simple

Thread.sleep(1)

inside the loop, which is only one milisecond, the CPU use dropped to almost zero as if I was not using the program, and the response time of the program was still pretty good on average (in my case it needed to reply things fast)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM