c# - FileSystemWatcher Dispose 调用挂起

标签 c# .net winforms filesystemwatcher

我们刚刚开始遇到 FileSystemWatcher 的一个奇怪问题,其中对 Dispose() 的调用似乎挂起。这段代码已经运行了一段时间没有任何问题,但我们刚刚升级到 .NET3.5 SP1,所以我想看看是否有其他人看到过这种行为。下面是创建 FileSystemWatcher 的代码:

if (this.fileWatcher == null)
{
   this.fileWatcher = new FileSystemWatcher();
}
this.fileWatcher.BeginInit();
this.fileWatcher.IncludeSubdirectories = true;
this.fileWatcher.Path = project.Directory;
this.fileWatcher.EnableRaisingEvents = true;
this.fileWatcher.NotifyFilter = NotifyFilters.Attributes;
this.fileWatcher.Changed += delegate(object s, FileSystemEventArgs args)
{
   FileWatcherFileChanged(args);
};
this.fileWatcher.EndInit();

它的使用方式是更新 TreeNode 对象的状态图像(略微调整以删除业务特定信息):

private void FileWatcherFileChanged(FileSystemEventArgs args)
{
   if (this.TreeView != null)
   {
      if (this.TreeView.InvokeRequired)
      {
         FileWatcherFileChangedCallback d = new FileWatcherFileChangedCallback(FileWatcherFileChanged);
         this.TreeView.Invoke(d, new object[]
      {
         args
      });
      }
      else
      {
         switch (args.ChangeType)
         {
            case WatcherChangeTypes.Changed:
               if (String.CompareOrdinal(this.project.FullName, args.FullPath) == 0)
               {
                  this.StateImageKey = GetStateImageKey();
               }
               else
               {
                  projectItemTreeNode.StateImageKey = GetStateImageKey();
               }
               break;
         }
      }
   }
}

我们是否遗漏了什么,或者这是 .NET3.5 SP1 的异常?

最佳答案

只是一个想法...这里是否有可能存在死锁问题?

您正在调用 TreeView.Invoke,这是一个阻塞调用。如果在您单击导致 FileSystemWatcher.Dispose() 调用的任何按钮时发生文件系统更改,您的 FileWatcherFileChanged 方法将在后台线程上调用并调用 TreeView.Invoke,这将阻塞直到您的表单线程可以处理 Invoke 请求.但是,您的表单线程将调用 FileSystemWatcher.Dispose(),它可能不会返回,直到处理完所有未决的更改请求。

尝试将 .Invoke 更改为 .BeginInvoke,看看是否有帮助。这可能会帮助您指明正确的方向。

当然,也可能是.NET 3.5SP1 的问题。我只是根据您提供的代码在这里推测。

关于c# - FileSystemWatcher Dispose 调用挂起,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73128/

相关文章:

c# - WPF C# 用户控制页面 IsVisibleChanged 事件

.net - 如何在代码中定义/更改 Linq To Sql 的映射

C# Winforms 设计器无法打开,因为它无法在同一程序集中找到类型

c# - datagridview 不允许用户删除行

c# - 创建唯一标识符,它是父标识符的可识别子标识符

c# - 与流程一起打印输出

c# - 无法将值类型数组转换为 params 对象 []

.net - 将表单的一个实例的 TextBox 控件的更改值更新到所有实例

c# - 关于在 C# 中构建 graphQL 查询的建议

c# - 在大文本模板中替换标记的最佳方法