zoukankan      html  css  js  c++  java
  • 框架设计——MVC IOC

    主要概念:

    注:以下概念是自我理解,不是很准确。

    • IOC:Inversion of Control(控制反转)。

    本来对象创建是通过使用类内部进行创建,现在把对象创建交给container(容器)管理

    打个比方好比现在华数网络(container),你去华数网络营业厅注册服务(普通电视,高清电视,华数网络),等你回家你接上电视,华数网络(container)就可以将普通电视或高清电视的对象返回给你;当你接上电脑时,华数网络(container)就将华数网络对象返回给你。

    • Unity

    Unity是微软的一款轻量级的容器。

    namespace MVCIOC.IOC
    {
        public class HttpContainerBuilder
        {
            public static readonly IUnityContainer UnityContainer = new UnityContainer();
    
            public static void Register()
            {
                //注册Service1和Service2
                UnityContainer.RegisterType(typeof (Service1));
                UnityContainer.RegisterType(typeof (Service2));
                //注册Control
                UnityContainer.RegisterType(typeof (HomeController));
            }
        }
    }

    这个往UnityContainer中注册了两个Servie1和Service2两种类型,并注册了HomeController

    namespace MVCIOC.IOC
    {
        public class UnityDependencyResolver : IDependencyResolver
        {
            IUnityContainer container;
            public UnityDependencyResolver(IUnityContainer UnityContainer)
            {
                this.container = UnityContainer;
            }
    
            public object GetService(Type serviceType)
            {
                return container.Resolve(serviceType);
            }
    
            public IEnumerable<object> GetServices(Type serviceType)
            {
                return container.ResolveAll(serviceType);
            }
        }
    }

     IDependencyResolver是依赖解析器接口

    protected void Application_Start()
            {
                HttpContainerBuilder.Register();
                DependencyResolver.SetResolver(new UnityDependencyResolver(HttpContainerBuilder.UnityContainer));
    
                AreaRegistration.RegisterAllAreas();
    
                RegisterGlobalFilters(GlobalFilters.Filters);
                RegisterRoutes(RouteTable.Routes);
            }

    注册类型,并设置依赖解析器(实现IDependencyResover接口的对象),这样UnityDependencyResolver接管了部分依赖注入类

    这样理论上里说,Sevice1,Service2,HomeControl类创建类型由Container容器来创建,感觉IOC与MVC已经完美结合了,但是运行以后就碰到了阻力。

     缺少一个IControllerFactory类,缺少类型映射。

    正如dudu所说我们总不能MVC中的所有接口都要注册一下,所以我们需要知道什么时候接受创建Controller,当Contorller所有准备都完成后,我们才接受创建Controller

       public class UnityControllerFactory : DefaultControllerFactory
        {
            protected override IController GetControllerInstance(System.Web.Routing.RequestContext requestContext, Type controllerType)
            {
                return (IController)HttpContainerBuilder.UnityContainer.Resolve(controllerType);
            }
    
        }

     这样我们在获取Controller时才从容器中解析对象,但是我们如果将那些没有在容器中注册过的类,实例化交给MVC自己实例

         public object GetService(Type serviceType)
            {
                if (container.IsRegistered(serviceType))
                {
                    return container.Resolve(serviceType);
                }
                return null;
            }

    当依赖解析器发现此类型没有注册过,就返回null,这样此类型的实例还有默认实例方式进行实例。 

    综上就可以将IOC与MVC完美结合了,总结如下:

    1.UnityContainner      通过方法RegisterType(Type)  注册类型

    2.UnityDependecyResolver:IDenpendecySolve

        定义依赖解析的方式,可以指定给MVC

    3.DependencyResolver.setResolver(第二点对象)    设置MVC依赖解析器

    4.GetService(Type type)

    获取解析对象,判断类型是否已注册  containner.IsRegistered(Type type),若没有注册,就返回null,还是采用默认获取对象方式

    5.UnityControllerFactory:DefaultControllerFactory

    重写GetControllerInstance(),将其从容器中获取对象

    如何保证容器中在一次Http请求中保证只有一个对象,所以要LifetimeManager(生命周期策略)

     这个下次再讲。

    • Autofac(推荐)

            Autofac在使用中发现,他比Unity更贴切MVC

           下载地址:http://code.google.com/p/autofac/downloads/list

           Autofac.dll  基础包

            Autofac.Integration.Mvc.dll  MVC包

     //注册数据库访问对象
                ContainerBuilder.RegisterType(contextType).InstancePerHttpRequest();
                //注册Service对象
                ContainerBuilder.RegisterAssemblyTypes(serviceAssembly).InstancePerHttpRequest();
                //注册仓储类
                ContainerBuilder.RegisterAssemblyTypes(repositoryAssembly).InstancePerHttpRequest();
    
    
                //注册Mvc控制器
                ContainerBuilder.RegisterControllers(webAssembly).InstancePerHttpRequest();
                //注册Mvc模型绑定管道
                ContainerBuilder.RegisterModelBinderProvider();
                //注册Mvc模型绑定器
                ContainerBuilder.RegisterModelBinders();
    
                Container = ContainerBuilder.Build();
                //Contoler的MVC解析点通过Container
                DependencyResolver.SetResolver(new AutofacDependencyResolver(Container));

    InstancePerHttpRequest:保证了生命周期策略,每次Http请求只实例化一次

    RegisterControllers:提供了单独注册Controller的方法

  • 相关阅读:
    【BZOJ2599】[IOI2011]Race 树的点分治
    【BZOJ1787】[Ahoi2008]Meet 紧急集合 LCA
    【BZOJ1834】[ZJOI2010]network 网络扩容 最大流+最小费用流
    【BZOJ3012】[Usaco2012 Dec]First! Trie树+拓补排序
    【BZOJ2743】[HEOI2012]采花 离线+树状数组
    【BZOJ2946】[Poi2000]公共串 后缀数组+二分
    【BZOJ2157】旅游 树链剖分+线段树
    【BZOJ2661】[BeiJing wc2012]连连看 最大费用流
    【BZOJ1801】[Ahoi2009]chess 中国象棋 DP
    【BZOJ4236】JOIOJI STL
  • 原文地址:https://www.cnblogs.com/cainiaoguoshi/p/3439299.html
Copyright © 2011-2022 走看看