订阅Singleton类发布的事件

ncf*_*ion 0 c# asp.net

我有一个名为CacheState的Singleton类.这个类发布了很多事件.CacheState有一个System.Timers.Timer,它循环并触发所有这些事件.

然后在我的asp.net应用程序中,我在Application_Start期间订阅了这些事件.CacheState中的Timer也在此期间启动:

protected void Application_Start(object sender, EventArgs e)
        {           
                CacheState.Instance.ProductChangedEvent += (objSender, argsE) => ProductService.ReloadProductCache(false);
                CacheState.Instance.PageflexChangedEvent += (objSender, argsE) => ProductService.ResetPageflexCache(false);
                CacheState.Instance.DeliveryChangedEvent += (objSender, argsE) => PricingRuleService.ResetDeliveryMethodsCache(false);
                CacheState.Instance.UIItemChangedEvent += (objSender, argsE) => TemplateService.ResetUIItemsCache(false);
                CacheState.Instance.ProductAttributeChangedEvent += Instance_ProductAttributeChangedEvent;
                CacheState.Instance.Start();

        }
Run Code Online (Sandbox Code Playgroud)

我读过C#Events会导致内存泄漏.那么,任何人都可以告诉我,如果我这样做错了吗?

谢谢.

And*_*eas 5

单例实例包含对已订阅其事件的所有对象的引用.如果这些对象不像单例实例那样存活,并且它们不会取消订阅这些事件,那么它们将保留在内存中.当您遇到内存泄漏时,这是唯一的情况.显然,如果事件源在您的侦听器之前被释放,则引用将被清除,如果您正确地取消注册侦听器,则也没有剩余引用.

要解决这个问题,您可以实现弱事件模式,或者IDisposable在所有侦听单例事件的对象中实现,确保它们在代码中正确处理!

当然,这不仅适用于单例对象,也适用于任何充当事件源的对象.然而,单例事件源是一个特别危险的情况,因为它通常只要您的应用程序运行就会存在,因此至少与任何其他对象一样长.