简体   繁体   English

while循环中的Thread.sleep()

[英]Thread.sleep() in a while loop

I notice that NetBeans is warning me about using Thread.sleep() in a while loop in my Java code, so I've done some research on the subject. 我注意到NetBeans警告我在我的Java代码中使用while循环中的Thread.sleep(),所以我已经对这个主题进行了一些研究。 It seems primarily the issue is one of performance, where your while condition may become true while the counter is still sleeping, thus wasting wall-clock time as you wait for the next iteration. 主要问题似乎是性能问题,当计数器仍处于休眠状态时,你的状态可能会变为真,因此在等待下一次迭代时会浪费挂钟时间。 This all makes perfect sense. 这一切都很有道理。

My application has a need to contact a remote system and periodically poll for the state of an operation, waiting until the operation is complete before sending the next request. 我的应用程序需要联系远程系统并定期轮询操作状态,等待操作完成后再发送下一个请求。 At the moment the code logically does this: 目前,代码在逻辑上执行此操作:

String state = get state via RPC call
while (!state.equals("complete")) {
    Thread.sleep(10000); // Wait 10 seconds
    state = {update state via RPC call}
}

Given that the circumstance is checking a remote operation (which is a somewhat expensive process, in that it runs for several seconds), is this a valid use of Thread.sleep() in a while loop? 鉴于情况是检查远程操作(这是一个有点昂贵的过程,因为它运行了几秒钟),这是一个在while循环中有效使用Thread.sleep()吗? Is there a better way to structure this logic? 有没有更好的方法来构建这个逻辑? I've seen some examples where I could use a Timer class, but I fail to see the benefit, as it still seems to boil down to the same straightforward logic above, but with a lot more complexity thrown in. 我已经看到了一些我可以使用Timer类的例子,但是我没有看到它的好处,因为它似乎仍然归结为上面相同的直接逻辑,但是引入了更多的复杂性。

Bear in mind that the remote system in this case is neither under my direct control, nor is it written in Java, so changing that end to be more "cooperative" in this scenario is not an option. 请记住,在这种情况下,远程系统既不是我的直接控制,也不是用Java编写的,因此在这种情况下将此端更改为“合作”不是一种选择。 My only option for updating my application's value for state is to create and send an XML message, receive a response, parse it, and then extract the piece of information I need. 我更新应用程序状态值的唯一选择是创建和发送XML消息,接收响应,解析它,然后提取我需要的信息。

Any suggestions or comments would be most welcome. 任何建议或意见都是最受欢迎的。

Unless your remote system can issue an event or otherwise notify you asynchronously, I don't think the above is at all unreasonable. 除非您的远程系统可以发出事件或以其他方式异步通知您,否则我认为上述情况完全不合理。 You need to balance your sleep() time vs. the time/load that the RPC call makes, but I think that's the only issue and the above doesn't seem of concern at all. 你需要平衡你的sleep()时间与RPC调用的时间/负载之间的平衡,但我认为这是唯一的问题,而上述内容似乎并不令人担忧。

Without being able to change the remote end to provide a "push" notification that it is done with its long-running process, that's about as well as you're going to be able to do. 无法更改远程端以提供“推送”通知,即通过其长时间运行的流程完成,这与您将能够做的一样。 As long as the Thread.sleep time is long compared to the cost of polling, you should be OK. 只要Thread.sleep时间比轮询成本长,你应该没问题。

You should (almost) never use sleep since its very inefficient and its not a good practice. 你应该(几乎)从不使用睡眠,因为它非常低效,而且不是一个好习惯。 Always use locks and condition variables where threads signal each other. 始终使用锁和条件变量,其中线程相互发出信号。 See Mike Dahlin's Coding Standards for Programming with threads 请参阅Mike Dahlin的线程编程编码标准

A template is: 模板是:

public class Foo{
  private Lock lock;
  private Condition c1;
  private Condition c2;

  public Foo()
  {
    lock = new SimpleLock();
    c1 = lock.newCondition();
    c2 = lock.newCondition();
    ...
  }

  public void doIt()
  {
    try{
      lock.lock();
      ...
      while(...){
        c1.awaitUninterruptibly();
      }
      ...
      c2.signal();
    }
    finally{
      lock.unlock();
    }
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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