8

我需要一种方法来跟踪各种类的实例,而这些类不知道它们正在被跟踪。本质上,我有一个类工厂,它创建实例并将它们交给另一个线程。一旦该线程完成并卸载实例,我需要得到通知,以便在所有实例都消失时进行引用计数并退出我的类工厂。

挑战在于我不能修改任何要加载的类,因为我无法控制它们的源代码。

跟踪我创建的实例很简单,我可以在创建它们时将它们放入某种集合中。跟踪他们的破坏给我带来了麻烦。如果我可以修改源代码,我会为每个类添加一个事件,当我创建一个实例时,我会挂钩该事件并将其用作我的通知。但我不能那样做。

所以,问题是这样的:有没有一种偷偷摸摸的方法来监视一个对象实例并检测它何时被破坏?

4

4 回答 4

11

由于您正在创建对象,因此您似乎可以返回一个装饰器而不是实际实例。

通过使用装饰器模式,您可以将返回的对象“包装”在您自己的装饰 API 中。装饰可以提供一个 IDisposable 实现,该实现提供您的销毁通知。

于 2010-07-16T18:37:48.073 回答
5

没有办法获得主动通知,但您可以保留WeakReference对象并定期检查是否有任何已死亡。

编辑:我比我更喜欢里德的回答!

于 2010-07-16T18:38:36.843 回答
2

如果您持有对您创建的实例的引用列表,它们将不会被垃圾收集,因此永远不会被销毁......

相反,您可以创建一个包含 Guid 列表的存储库,并为每个实例创建一个新的 Guid,然后将其添加到列表中 - 类似于 FactoryRepository。通过这种方式,您不会遇到垃圾收集的引用问题,因为 Guid 是结构而不是引用类型。然后,您可以从每个类继承以创建可以在销毁时通知的类型。我假设由于您无法更改原始类的代码,因此您也无法更改这些类的使用者,因此装饰器模式(通过接口)之类的东西不存在,因为类型不兼容。

非常简化的例子:

public class OriginalClassDestroyNotifier : OriginalClass
{
    private readonly Guid _instanceId;

    public OriginalClassDestroyNotifier(Guid instanceId)
    {
        _instanceId = instanceId;
    }

    ~OriginalClassDestroyNotifier()
    {
        FactoryRepository.NotifyDestroyed(_instanceId);
    }
}
于 2010-07-16T18:46:55.027 回答
1

你如何控制对象的销毁:

public void Destroy(T obj)
{
    if (obj == null)
        throw new ArgumentNullException("obj");
    if (!_living.Contains(obj))
        throw new ArgumentException("Where did this obj come from?");

    using (obj as IDisposable)
    {

    }

    _living.Remove(obj); // List?
}
于 2010-07-16T18:34:37.287 回答