我想让主线程保持活动状态。 我找到了3个选项,我不知道哪个是最好的。 有什么区别?为什么?
其中有浪费资源吗?
while(true){}
thread.join()
CountDownLatch(1).await()
我尝试过,并且效果很好。
while(true){}
thread.join()
CountDownLatch(1).await()
答案 0 :(得分:4)
这里:
while(true){}
进行“热”等待。这意味着:您的CPU以100%的速度旋转,什么也不做。也许,也许,如果您真的很幸运,JVM会检测到这一点,并且不会像这样消耗CPU周期。
对于join(),我们发现:
当我们在线程上调用join()方法时,调用线程进入等待状态。它一直处于等待状态,直到引用的线程终止。
(来自此tutorial)
因此,join()听起来更健康。 await()
应该以类似的方式工作。
这两种方法的缺点:它们对线程中断做出反应,因此将它们置于“ while true”循环中可能是一个好主意。
答案 1 :(得分:3)
其中有浪费资源吗?
无限循环会毫无意义地浪费资源,因为它会无缘无故地进行迭代,并且会消耗计算时间和精力。
另外两个不应浪费资源,因为它们允许操作系统在被阻塞的同时执行其他线程。
答案 2 :(得分:2)
他们自己都不足够。
while(true){}
无休止的繁忙循环永远在处理器上旋转,从而产生热量并消耗电量。它不能干净地停下来。
thread.join()
等待另一个线程完成。这与其他方法不同,因为它实际上可以完成,而不是永远运行。但是,如果应用程序仅由运行直到完成的另一个线程组成,那么为什么不从主线程运行代码,而不是创建另一个线程并等待它完成呢?
CountDownLatch(1).await()
创建监视器并永久等待。这几乎与:
Object o = new Object();
synchronized (o) {
o.wait();
}
同样,没有干净的方法来停止程序。
最后一个是CountdownLatch,它最接近可以使用的方法。与其立即丢弃对闩锁的引用,不如将其传递给控制执行的代码,以便它可以告知主线程该停止了。但是,CountdownLatch本身作为退出条件的信号令人困惑。退出信号是布尔值,因此信号量会更合适
Semaphore exitPermission = new Semaphore(0);
// Pass exit permission around.
exitPermission.acquire();
但这仍然允许接收者弄乱状态(通过尝试获取状态并弄乱调度),因此信号量应隐藏在仅允许其他人释放状态的接口后面。