ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

C#-简单注入器-装饰器导致容器未被垃圾收集?

2019-11-19 16:07:47  阅读:261  来源: 互联网

标签:dependency-injection memory-leaks c simple-injector


我注意到,当我通过简单的注入器添加装饰器时,该容器不会超出范围.有人知道这是否可以预期吗?如果我不添加装饰器,则说明该容器是垃圾收集的.否则,不是.我应该采取什么措施来强制清理?

这是一个简单的例子.如果添加了装饰器,则在“运行”完成后,容器仍在内存中.如果未添加装饰器,则容器将进行GC处理.

public interface IDoSomething { }
public class DoSomething: IDoSomething { }
public class DoSomethingDec1: IDoSomething {
    public DoSomethingDec1(IDoSomething handler) { }
}
public class DoSomethingDec2 : IDoSomething {
    public DoSomethingDec2(IDoSomething handler) { }
}

static void Main(string[] args) {
    Console.WriteLine("Press a key to start");
    Console.ReadKey(true);
    Run();
    GC.Collect();
    Console.WriteLine("Done");
    Console.ReadKey(true);
}

static void Run() {
    //can be re-created with 1 container; easier to see with multiple
    for (var i = 0; i < 1000; i++) {
        using (var container = new Container()) {
            container.Register<IDoSomething, DoSomething>();

            //Comment out these 2 lines to remove the decorators
            container.RegisterDecorator<IDoSomething, DoSomethingDec1>();
            container.RegisterDecorator<IDoSomething, DoSomethingDec2>();

            container.Verify();

            container.GetInstance<IDoSomething>();
        }
    }
}

带装饰器:

enter image description here

没有装饰器:

enter image description here

解决方法:

更新:此问题已在v3.1.1中修复.

该问题是由bug in the .NET framework引起的,如果该图包含ThreadLocal< T&gt ;,则该对象使循环对象图保持活动状态.在简单注入器的情况下,装饰器子系统添加ThreadLocal< T>.到“容器的项目”字典中. ThreadLocal的值再次间接引用了Container,从而导致图形变为循环的.由于.NET中的错误,因此ThreadLocal< T>被认为是活动的,保持其依赖对象(例如Container)活动. Container实例再次使其他所有内容保持活动状态,这显然会导致内存泄漏.

尽管我们可以等待Microsoft解决此问题,但这可能会花费太长时间.因此,我们的计划是在将来的修补程序版本中解决此问题.我们可能会替换.NET的ThreadLocal< T>.使用我们自己的自定义实现,不会导致内存泄漏.该自定义实现已在Simple Injector的PCL库中使用,因为ThreadLocal< T>不适用于PCL.这意味着PCL版本的Simple Injector不存在此问题.

标签:dependency-injection,memory-leaks,c,simple-injector
来源: https://codeday.me/bug/20191119/2037255.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有