有一段时间(真正的)无限循环挂在CPU上吗?

时间:2014-08-18 17:16:28

标签: c# while-loop infinite-loop

我遇到一种情况,我需要在服务中运行一个常量循环,每次检查某些条件,然后采取适当的措施。从设计角度来看,使用while (true)循环非常合适:

while (true)
{
    Process();
}

我看到一些引用会占用不必要的CPU周期,我应该使用Timer,或者将Thread.Sleep添加到循环中。我还看过帖子说使用while (true)没有错。

在我的开发机器上,它似乎没有负面影响,尽管CPU使用率确实上升了。可能是CPU使用率分布在多个核心上,其中部署环境可能只有一个核心。

while (true)循环是否会对CPU产生负面影响,如果是,那么减轻影响的正确方法是什么?

修改

Process()方法检查内存(快速)数据存储的状态。如果根据状态发现有工作要做,则使用Task.Run()处理它(因此控制立即返回循环)。

2 个答案:

答案 0 :(得分:4)

答案当然是取决于你在做什么

while(true)循环本身并不会导致其自身性能下降。性能危险发生在方法体中,在本例中为Process()

如果该方法打算永远运行并且永远不会休息,那么此构造就可以了。但是,如果Process应该对事件做出回应,或者“听”'如果发生某种情况,将其置于while(true)循环中会导致处理器进行不必要的轮询。

例如,

while (true)
{
   //At the start of every minute
   if (DateTime.Now.Seconds == 0)
       //Do Something
}

这将是非常糟糕的。你让CPU经常检查一个条件,这个条件每分钟只执行一次,并阻止CPU在剩余的时间内完成有用的工作。

在这种情况下,您最好使用Threading命名空间中可用的某些功能来释放CPU。

答案 1 :(得分:2)

在合作多任务系统中,这确实可以固定CPU(或至少一个核心)。

但是,大多数现代操作系统采用抢占式多任务处理,这基本上意味着操作系统控制着您的进程需要多长时间。因此,尽管您的循环将使用100%的线程(或可能是进程的)时间,并且剥夺其他人某些 CPU时间,但操作系统将确保准备运行的其他进程/线程获得时间这样做。所以在最坏的情况下,你会减慢一些事情。

你要特别注意的一件事是,这样的循环将占用运行它的线程,使得该线程不可用于其他东西。因此,您不希望在UI线程上执行此操作。 (有Application.DoEvents(),但你必须经常自己调用它,它的使用表明你正在做一些真正属于它自己的线程的东西。)