Ioc 之 Unity的依赖注入
Unity是微软官方提供的一个Ioc容器,用来实现依赖注入,减少代码之间的耦合程度。使用Unity实现Ioc方式有两种,一种是使用代码方式实现,一种是利用配置文件来实现。
我们先来看一下代码方式是如何实现的。我们先定义 IPay接口,IOrder接口,再定义WeChatPay,AliPay,Order三个类。
/// <summary>
/// 支付接口
/// </summary>
public interface IPay
{
string Pay();
} public interface IOrder
{
string ToPay();
}
/// <summary>
/// 微信支付
/// </summary>
public class WeChatPay :IPay
{
public string Pay()
{
return "微信支付";
}
}
/// <summary>
/// 支付宝支付
/// </summary>
public class AliPay : IPay
{
public string Pay()
{
return "支付宝支付";
}
}
/// <summary>
/// 订单
/// </summary>
public class Order : IOrder
{
/// <summary>
/// 订单支付方式
/// </summary>
public IPay _iPay; //构造函数注入:可以不写,因为Unity解析时默认会找参数最多的构造函数
[InjectionConstructor]
public Order(IPay iPay)
{
_iPay = iPay;
} [Dependency]//属性注入
public IPay _iPayProperty { get; set; } [InjectionMethod]//方法注入
public void PayInit(IPay ipay)
{
this._iPay = ipay;
} public string ToPay()
{
return this._iPay.Pay();
}
}
接着,我们可以使用代码的方式来使用Unity
//创建一个Unity空容器
IUnityContainer container = new UnityContainer(); //向Unity容器注入WeChatPay
container.RegisterType<IPay, WeChatPay>();
//向Unity容器注入AliPay,使用命名注册,解析的时候也需要使用命名获取实例
container.RegisterType<IPay, AliPay>("alipay"); var obj = container.Resolve<IPay>();
Console.WriteLine(obj.Pay());
obj = container.Resolve<IPay>("alipay");
Console.WriteLine(obj.Pay()); container.RegisterType<IOrder, Order>();
//Unity解析的时候会按照:构造函数注入 --> 属性注入 --> 方法注入的顺序进行解析
var order = container.Resolve<IOrder>();
Console.WriteLine($"Order.ToPay: {order.ToPay()}");
Console.ReadLine();
运行得到结果

那么,Unity注入类型的生命周期有哪些呢?
//生命周期
IUnityContainer container = new UnityContainer(); //默认瞬时,每一次都是全新生成
container.RegisterType<IOrder, Order>();
container.RegisterType<IOrder, Order>(new TransientLifetimeManager()); //容器单例
container.RegisterType<IOrder, Order>(new ContainerControlledLifetimeManager()); //线程单例
container.RegisterType<IOrder, Order>(new PerThreadLifetimeManager());
var phone1 = container.Resolve<IPhone>();
var phone2 = container.Resolve<IPhone>();
Console.WriteLine(object.ReferenceEquals(phone1, phone2)); //结果为true //分级容器单例
container.RegisterType<IOrder, Order>(new HierarchicalLifetimeManager());
IUnityContainer childContainer = container.CreateChildContainer(); //外部可释放单例
container.RegisterType<IOrder, Order>(new ExternallyControlledLifetimeManager()); //循环引用 不推荐
container.RegisterType<IOrder, Order>(new PerResolveLifetimeManager());
接下来我们再来看下Unity使用配置文件的方式该如何实现依赖注入。我们在项目中新建一个文件夹Config,然后再创建unity.config文件。
<configuration>
<configSections>
<!--<section name="unity" type="Microsoft.Practices.Unity.Configuration.UnityConfigurationSection, Microsoft.Practices.Unity.Configuration"/>-->
<section name="unity" type="Microsoft.Practices.Unity.Configuration.UnityConfigurationSection, Unity.Configuration"/>
</configSections>
<unity>
<!--<sectionExtension type="Microsoft.Practices.Unity.InterceptionExtension.Configuration.InterceptionConfigurationExtension, Microsoft.Practices.Unity.Interception.Configuration"/>-->
<sectionExtension type="Microsoft.Practices.Unity.InterceptionExtension.Configuration.InterceptionConfigurationExtension, Unity.Interception.Configuration"/>
<containers> <container name="IocContainer">
<!-- 格式:类名,程序集名称 -->
<register type="IocDemo.IService.IOrder,IocDemo.IService" mapTo="IocDemo.Service.Order, IocDemo.Service"/>
<register type="IocDemo.IService.IPay,IocDemo.IService" mapTo="IocDemo.Service.AliPay, IocDemo.Service" name="alipay"/>
<register type="IocDemo.IService.IPay, IocDemo.IService" mapTo="IocDemo.Service.WeChatPay, IocDemo.Service"/>
</container>
</containers>
</unity>
</configuration>
然后在程序中使用ExeConfigurationFileMap来装载该配置文件
ExeConfigurationFileMap fileMap = new ExeConfigurationFileMap();
fileMap.ExeConfigFilename = Path.Combine(AppDomain.CurrentDomain.BaseDirectory + "Config\\unity.config");//找配置文件的路径
Configuration configuration = ConfigurationManager.OpenMappedExeConfiguration(fileMap, ConfigurationUserLevel.None);
UnityConfigurationSection section = (UnityConfigurationSection)configuration.GetSection(UnityConfigurationSection.SectionName); IUnityContainer container = new UnityContainer();
section.Configure(container, "IocContainer"); IOrder order = container.Resolve<IOrder>();
Console.WriteLine(order.ToPay()); IPay aliPay = container.Resolve<IPay>("alipay");
Console.WriteLine(aliPay.Pay()); Console.ReadLine();

我们也可以在配置文件中指定生命周期,构造函数初始值
<register type="IocDemo.IService.IOrder,IocDemo.IService" mapTo="IocDemo.Service.Order,IocDemo.Service">
<lifetime type="transient" />
<constructor>
<!--<param name="id" type="System.Int32" value="" />-->
<param name="iPay" type="IocDemo.IService.IPay,IocDemo.IService"></param>
</constructor>
</register>
Ioc 之 Unity的依赖注入的更多相关文章
- IOC使用Unity 实现依赖注入
转自:http://www.cnblogs.com/techborther/archive/2012/01/06/2313498.html http://www.cnblogs.com/xishuai ...
- Entity Framework 实体框架的形成之旅--利用Unity对象依赖注入优化实体框架(2)
在本系列的第一篇随笔<Entity Framework 实体框架的形成之旅--基于泛型的仓储模式的实体框架(1)>中介绍了Entity Framework 实体框架的一些基础知识,以及构建 ...
- .NET 使用unity实现依赖注入
原文地址:http://www.cnblogs.com/wujy/p/3317795.html 一:理论部分 依赖注入:这是 Ioc 模式的一种特殊情况,是一种基于改变对象的行为而不改变类的内部的接口 ...
- ASP.NET MVC中使用Unity进行依赖注入的三种方式
在ASP.NET MVC中使用Unity进行依赖注入的三种方式 2013-12-15 21:07 by 小白哥哥, 146 阅读, 0 评论, 收藏, 编辑 在ASP.NET MVC4中,为了在解开C ...
- 运用Unity实现依赖注入[结合简单三层实例]
运用Unity实现依赖注入[结合简单三层实例] 一:理论部分 依赖注入:这是 Ioc 模式的一种特殊情况,是一种基于改变对象的行为而不改变类的内部的接口编程技术.开发人员编写实现接口的类代码,并基于接 ...
- Spring IOC(三)依赖注入
本系列目录: Spring IOC(一)概览 Spring IOC(二)容器初始化 Spring IOC(三)依赖注入 Spring IOC(四)总结 目录 1.AbstractBeanFactory ...
- Spring IOC(五)依赖注入
Spring IOC(五)依赖注入 Spring 系列目录(https://www.cnblogs.com/binarylei/p/10198698.html) 一.autowire 五种注入方式测试 ...
- 在 mvc 4 中使用 unity 进行依赖注入
在 mvc 4 中使用 unity 进行依赖注入 关于依赖注入的概念,这里就不再叙述了,我们用 mvc 4 结合 unity,使用构造函数来进行依 赖注入.具体步骤如下: 1. 首先建立 一个 mvc ...
- 深入浅出spring IOC中三种依赖注入方式
深入浅出spring IOC中三种依赖注入方式 spring的核心思想是IOC和AOP,IOC-控制反转,是一个重要的面向对象编程的法则来消减计算机程序的耦合问题,控制反转一般分为两种类型,依赖注入和 ...
随机推荐
- oracle报ORA-00911:invalid character
转自:http://www.cnblogs.com/chuang-sharing/p/9493316.html 今天查问题的时候,发现一个在分号后边加注释,解析错误的问题: select decode ...
- web安全之XSS攻击原理及防范
阅读目录 一:什么是XSS攻击? 二:反射型XSS 三:存储型XSS 四:DOM-based型XSS 五:SQL注入 六:XSS如何防范? 1. cookie安全策略 2. X-XSS-Protect ...
- hdu 4704 Sum【组合数学/费马小定理/大数取模】By cellur925
首先,我们珂以抽象出S函数的模型:把n拆成k个正整数,有多少种方案? 答案是C(n-1,k-1). 然后发现我们要求的是一段连续的函数值,仔细思考,并根据组合数的性质,我们珂以发现实际上答案就是在让求 ...
- 项目上线后出现Bug,该如何处理?
项目在上线之后又出现了Bug,这让很多测试人员和开发人员头痛.但很多时候线上Bug普遍地存在,不可避免. 任何项目都存在未发现 Bug 和 已发现 Bug 两种情况,不存在没有 Bug的情况. 即 ...
- Python转载
让Python的经验更多一点 Python while 1 和 while True 速度比较 Python %s和%r的区别
- 关于C_Cpp的一些小结
## 某些函数的使用 1. printf / sprintf / fprintf printf:把格式字符串输出到标准输出(可重定向) sprintf:把格式字符串输出到指定字符串中,参数比print ...
- HDFS Java API
HDFS Java API 搭建Hadoop客户端与Java访问HDFS集群
- set+线段树 Codeforces Round #305 (Div. 2) D. Mike and Feet
题目传送门 /* 题意:对于长度为x的子序列,每个序列存放为最小值,输出长度为x的子序列的最大值 set+线段树:线段树每个结点存放长度为rt的最大值,更新:先升序排序,逐个添加到set中 查找左右相 ...
- HDU 5808 Price List Strike Back bitset优化的背包。。水过去了
http://acm.hdu.edu.cn/showproblem.php?pid=5808 用bitset<120>dp,表示dp[0] = true,表示0出现过,dp[100] = ...
- ES--在windows上快速安装
环境准备 java环境部署: Java下载路径:http://download.oracle.com/otn-pub/java/jdk/8u181-b13/96a7b8442fe848ef90c96a ...