我需要保留对 FileSystemWatcher 的引用吗?

发布于 2025-01-01 22:45:01 字数 600 浏览 6 评论 0原文

我正在使用 FileSystemWatcher (在 ASP.NET Web 应用程序中)来监视文件的更改。观察者是在 Singleton 类的构造函数中设置的,例如:

private SingletonConstructor()
{
    var fileToWatch = "{absolute path to file}";
    var fsw = new FileSystemWatcher(
        Path.GetDirectoryName(fileToWatch),
        Path.GetFileName(fileToWatch));
    fsw.Changed += OnFileChanged;
    fsw.EnableRaisingEvents = true;
}

private void OnFileChanged(object sender, FileSystemEventArgs e)
{
    // process file...
}

到目前为止一切正常。但我的问题是:

使用局部变量(var fsw)设置观察程序是否安全?或者我应该在私有字段中保留对它的引用以防止它被垃圾收集?

I'm using a FileSystemWatcher (in an ASP.NET web app) to monitor a file for changes. The watcher is set up in the constructor of a Singleton class, e.g:

private SingletonConstructor()
{
    var fileToWatch = "{absolute path to file}";
    var fsw = new FileSystemWatcher(
        Path.GetDirectoryName(fileToWatch),
        Path.GetFileName(fileToWatch));
    fsw.Changed += OnFileChanged;
    fsw.EnableRaisingEvents = true;
}

private void OnFileChanged(object sender, FileSystemEventArgs e)
{
    // process file...
}

Everything works fine so far. But my question is:

Is it safe to setup the watcher using a local variable (var fsw)? Or should I keep a reference to it in a private field to prevent it from being garbage collected?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

真心难拥有 2025-01-08 22:45:01

在上面的示例中,FileSystemWatcher 之所以保持活动状态,只是因为属性 EnableRaisingEvents 设置为 true。事实上,Singleton 类有一个注册到 FileSystemWatcher.Changed 事件的事件处理程序,这对于 fsw 是否有资格进行垃圾回收没有任何直接影响。有关详细信息,请参阅事件处理程序是否会阻止垃圾回收的发生?信息。

以下代码显示,将 EnableRaisingEvents 设置为 false 时,FileSystemWatcher 对象将被垃圾回收:一旦 GC.Collect() 时,WeakReference 上的 IsAlive 属性为 false

class MyClass
{
    public WeakReference FileSystemWatcherWeakReference;
    public MyClass()
    {
        var fileToWatch = @"d:\temp\test.txt";
        var fsw = new FileSystemWatcher(
            Path.GetDirectoryName(fileToWatch),
            Path.GetFileName(fileToWatch));
        fsw.Changed += OnFileChanged;
        fsw.EnableRaisingEvents = false;
        FileSystemWatcherWeakReference = new WeakReference(fsw);
    }

    private void OnFileChanged(object sender, FileSystemEventArgs e)
    {
        // process file... 
    }

}

class Program
{
    static void Main(string[] args)
    {
        MyClass mc = new MyClass();
        GC.Collect();
        Console.WriteLine(mc.FileSystemWatcherWeakReference.IsAlive);
    }
}

In the example above FileSystemWatcher is kept alive only because the property EnableRaisingEvents is set to true. The fact that the Singleton class has an event handler registered to FileSystemWatcher.Changed event does not have any direct bearing on fsw being eligible for Garbage collection. See Do event handlers stop garbage collection from occurring? for more information.

The following code shows that with EnableRaisingEvents set to false, the FileSystemWatcher object is garbage collected: Once GC.Collect() is called, the IsAlive property on the WeakReference is false.

class MyClass
{
    public WeakReference FileSystemWatcherWeakReference;
    public MyClass()
    {
        var fileToWatch = @"d:\temp\test.txt";
        var fsw = new FileSystemWatcher(
            Path.GetDirectoryName(fileToWatch),
            Path.GetFileName(fileToWatch));
        fsw.Changed += OnFileChanged;
        fsw.EnableRaisingEvents = false;
        FileSystemWatcherWeakReference = new WeakReference(fsw);
    }

    private void OnFileChanged(object sender, FileSystemEventArgs e)
    {
        // process file... 
    }

}

class Program
{
    static void Main(string[] args)
    {
        MyClass mc = new MyClass();
        GC.Collect();
        Console.WriteLine(mc.FileSystemWatcherWeakReference.IsAlive);
    }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文