【问题标题】:Form freezes during while loop表单在while循环期间冻结
【发布时间】:2014-01-15 22:59:48
【问题描述】:

我有一段代码可以检查某个应用程序是否正在运行

while (Process.GetProcessesByName("notepad").Length == 0)
{
     System.Threading.Thread.Sleep(1000);
}

它会检查用户是否正在运行记事本,但它会使表单冻结并在几秒钟后停止响应。不知道有没有更好的办法解决这个问题。

【问题讨论】:

    标签: c# forms while-loop


    【解决方案1】:

    在这种情况下,您实际上希望在与主 UI 线程分开的线程上完成一些工作。

    理想的情况是利用BackgroundWorker 对象,它会很高兴地在另一个线程上运行,并且不会阻塞您的 UI。

    我不会给你一个完整的解释,因为那里有很多教程,但你会想要做一些类似的事情:

    var worker = new BackgroundWorker();
    worker.DoWork += new DoWorkEventHandler(worker_DoWork);
    

    这将创建 BackgroundWorker 并将其 DoWork 事件绑定到我们即将创建的 workerDoWork 处理程序:

     void worker_DoWork(object sender, DoWorkEventArgs e)
     {
        //Glorious time-consuming code that no longer blocks!
        while (Process.GetProcessesByName("notepad").Length == 0)
        {
            System.Threading.Thread.Sleep(1000);
        }
     }
    

    现在启动worker:

     worker.RunWorkerAsync();
    

    查看本教程:http://www.codeproject.com/Articles/99143/BackgroundWorker-Class-Sample-for-Beginners

    【讨论】:

    • 唯一的问题是它不会等待后台工作人员完成他的工作。
    • 什么不会等? BackgroundWorker 对象有一些额外的技巧,但我不太明白你在尝试什么。查看教程和文档,那里有更多详细信息。
    • @badkip - Windows 是事件驱动的,您的程序也应该以这种方式工作。不要“等待”某事发生,对状态变化做出反应。
    【解决方案2】:

    表单冻结,因为您的代码在 UI/主线程上运行。
    因此,因为您在记事本未打开时正在休眠线程,所以您的表单将被锁定。
    如果您异步运行代码,那么您将工作线程从 UI 移开。
    在这里查看C# async overview

    【讨论】:

      【解决方案3】:

      您总是可以只启动一个异步任务来不断更新 UI

      Task f = Task.Factory.StartNew(() =>
              {
                  while (true)
                  {
                      //This would make the form become responsive every 500 ms
                      Thread.Sleep(500); //Makes the async thread sleep for 500 ms
                      Application.DoEvents(); //Updates the Form's UI
                  }
              });
      

      或者这个在不同的线程上运行它

      Task f = Task.Factory.StartNew(() =>
      {
      while (Process.GetProcessesByName("notepad").Length == 0)
          {
              System.Threading.Thread.Sleep(1000); //Does the while loop every 1000 ms
          }
      });
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2017-10-20
        • 1970-01-01
        • 1970-01-01
        • 2015-01-28
        • 1970-01-01
        • 1970-01-01
        • 2019-04-09
        相关资源
        最近更新 更多