首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >互斥阻塞UI线程

互斥阻塞UI线程
EN

Stack Overflow用户
提问于 2015-02-02 22:27:36
回答 1查看 557关注 0票数 0

我的应用程序中有后台线程,它使用互斥量,如下所示:

代码语言:javascript
复制
  void bgWorker_DoWork(object sender, DoWorkEventArgs e)
    {
      MyMutex.MuImageLock.WaitOne();                
      foreach (var file in ImageFiles)
      {
          SyncFileToLocalImage(file.FileNameNoPath);
      }
       MyMutex.MuImageLock.ReleaseMutex();          
    }

同步大约需要2-3分钟。现在我的应用程序中又多了一个后台线程,它们做同样的事情只是为了确保。

我的问题是,在我开始我的第二个线程之前,我想检查互斥是否可用。如果它不可用,这意味着另一个线程正在运行,那么我不需要启动这个新线程。所以使用下面的代码来检查我。

但是使用下面的代码,WaitOne方法会阻塞我的UI线程,直到前一个线程不释放互斥锁。

代码语言:javascript
复制
if (MyMutex.MuImageLock.WaitOne())
{
   getPRImages();
   MyMutex.MuImageLock.ReleaseMutex();
}

我不想阻塞当前的UI线程,我只想看看互斥是否可用。我该怎么做呢?

EN

回答 1

Stack Overflow用户

发布于 2015-02-03 13:05:43

在您的代码示例中,除了后台线程本身,您似乎没有使用BackgroundWorker的任何特性。因此,正确的方法是简单地保留一个标志,并使用Task.Run()启动后台进程:

代码语言:javascript
复制
private bool _isRunning;

private async void Button_Click(object sender, RoutedEventArgs e)
{
    if (_isRunning)
    {
        return;
    }

    _isRunning = true;
    await Task.Run(() => SyncAllFiles());
    _isRunning = false;

    // Populate ListBox here
}

private void SyncAllFiles()
{
    foreach (var file in ImageFiles)
    {
        SyncFileToLocalImage(file.FileNameNoPath);
    }
}

注意:在上面的代码中,我假设有一些UI按钮可以启动同步。不幸的是,您的问题没有包含足够完整的代码示例来理解上下文。假设,如果不是一个按钮,您可以调整以上内容以适应您的特定场景。

即使您正在报告进度,只是碰巧在您的问题的代码示例中遗漏了这一点,您仍然可以执行上述操作。只需使用Progress类,将该类的一个实例传递给SyncAllFiles()方法并调用IProgress<T>.Report()方法来实际报告进度。这将与BackgroundWorker.ProgressChanged事件的工作方式相同,因为事件处理程序将在UI线程上调用(只要您在UI线程上创建Progress<T>对象)。

请注意,比上面更好的做法是禁用按钮或其他允许用户再次启动操作的UI元素,只有在操作完成时才重新启用它。

最后:我不认为有一种实用的方法来使用Mutex类(您在帖子中没有具体说明,但我假设您使用的是System.Threading.Mutex)。依赖于互斥锁来协调操作,而UI线程看起来就像是在请求难以解决的竞争条件。例如,如果你的按钮上有两个连续的点击事件,在后台线程可以启动并获取互斥之前处理第二个事件会怎么样呢?这只是它可能出错的许多可能方式之一。

上面提出的解决方案,由于完全在单个线程中管理状态,将确保直接解决所有竞争条件。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/28279939

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档