原文

In my previous post Service Locator Pattern in C#: A Simple Example I introduced a fairly basic implementation of this pattern. In this post I will address one of the limitations of that implementation, introducing a form of lazy initialization.

Defining Lazy Initialization

Lazy initialization improves the performance of object creation, deferring long running initializations until they are really needed.

Suppose for example that some of the fields of an object need to be read from the database. If a client never access those fields, accessing the database to retrieve those fields has been useless and it has just made object initialization slower (often by a considerable factor).

Martin Fowler credits Kent Beck with the introduction of the lazy initialization pattern, and in PoEAA book he describes it in the following way:

The basic idea is that every access to the field checks to see if it’s null. If so, it calculates the value of the field before returning the field. To make this work you have to ensure that the field is self-encapsulated, meaning that all access to the field, even from within the class, is done through a getting method.

Fairly simple.

The Improved Service Locator

The following is the improved version of the service locator which uses lazy initialization of the services.

internal class ServiceLocator : IServiceLocator
{// a map between contracts -> concrete implementation classesprivate IDictionary<Type, Type> servicesType;// a map containing references to concrete implementation already instantiated// (the service locator uses lazy instantiation).private IDictionary<Type, object> instantiatedServices;internal ServiceLocator(){this.servicesType = new Dictionary<Type, Type>();this.instantiatedServices = new Dictionary<Type, object>();this.BuildServiceTypesMap();}public T GetService<T>(){if (this.instantiatedServices.ContainsKey(typeof(T))){return (T)this.instantiatedServices[typeof(T)];}else{// lazy initializationtry{// use reflection to invoke the serviceConstructorInfo constructor = servicesType[typeof(T)].GetConstructor(new Type[0]);Debug.Assert(constructor != null, "Cannot find a suitable constructor for " + typeof(T));T service = (T)constructor.Invoke(null);// add the service to the ones that we have already instantiatedinstantiatedServices.Add(typeof(T), service);return service;}catch (KeyNotFoundException){throw new ApplicationException"The requested service is not registered");}}}private void BuildServiceTypesMap(){servicesType.Add(typeof(IServiceA),typeof(ServiceA));servicesType.Add(typeof(IServiceB),typeof(ServiceB));servicesType.Add(typeof(IServiceC),typeof(ServiceC));}
}

We are now maintaining two separate maps:

  • servicesType maps an interface describing a service to a type T that implements that interface.
  • instantiatedServices maps an interface to an instantiated object of class T.

Both maps are initialized in the constructor. However only the first map is filled. Every time GetService is invoked, we check whether a concrete implementation of that service has already been created. If not, we create that service implementation retrieving its constructor via reflection, and we put a reference to that implementation in the instantiatedServices map.

For this to work, the service implementation needs to expose a default (parameterless) constructor.

If services creation time is significant, lazy initialization can save you quite some time during application start up, with very little cost in terms of increased complexity.

Next article in the series: A Singleton Service Locator

转载于:https://www.cnblogs.com/philzhou/archive/2011/03/07/1974493.html

Service Locator Pattern in C# with Lazy Initialization(转)相关推荐

  1. 设计模式 - 服务定位模式 Service Locator Pattern

    译者序:看 spring framework 时候了解到的 Service Locator 模式,顺便搜到了这篇文章,感觉很棒,顺手翻译下,好安利给其他小伙伴. 原文链接:http://gamepro ...

  2. 三十六、服务定位器模式 (Service Locator Pattern)

    服务定位器模式(Service Locator Pattern)用于想使用 JNDI 查询定位各种服务的时候 考虑到为某个服务查找 JNDI 的代价很高,服务定位器模式充分利用了缓存技术 在首次请求某 ...

  3. 设计模式のService Locator Pattern

    Service Locator Pattern 学习 spring 的时候遇到的一个设计模式. 关于此设计模式的geeksforgeeks的原文 ,我理解性的翻译了下,添加了些自己的理解. 用 抽象层 ...

  4. Design Pattern - Service Locator Pattern--转载

    原文地址:http://www.tutorialspoint.com/design_pattern/service_locator_pattern.htm The service locator de ...

  5. Service Locator 模式

    什么是Service Locator 模式? 服务定位模式(Service Locator Pattern)是一种软件开发中的设计模式,通过应用强大的抽象层,可对涉及尝试获取一个服务的过程进行封装.该 ...

  6. (转载)Service Locator模式(简单的IOC容器实现 MVVMLight SimpleIoc)

    转载自:https://www.cnblogs.com/gaochundong/archive/2013/04/12/service_locator_pattern.html 什么是Service L ...

  7. 单例模式的两种实现方式对比:DCL (double check idiom)双重检查 和 lazy initialization holder class(静态内部类)...

    首先这两种方式都是延迟初始化机制,就是当要用到的时候再去初始化. 但是Effective Java书中说过:除非绝对必要,否则就不要这么做. 1. DCL (double checked lockin ...

  8. php service locator,Yii源码解读-服务定位器(ServiceLocator)

    SL的目的也是解耦,并且非常适合基于服务和组件的应用. Service Locator充当了一个运行时的链接器的角色,可以在运行时动态地修改一个类所要选用的服务, 而不必对类作任何的修改. 一个类可以 ...

  9. 2.5 lazy initialization

    文章目录 保护共享数据的初始化过程 std::call_once std::call_once 的替代方案 保护共享数据的初始化过程 lazy initialization (延迟初始化)在单线程的代 ...

最新文章

  1. 流利说流年不利,市值跌去80%,AI教育第一股营收赚钱仍然依赖人工
  2. 谈谈java的BlockingQueue
  3. arduino定时器控制舵机_Arduino学习经验(一)之解决舵机库和pwm输出冲突
  4. 1xx、101、100 状态详解
  5. linux下的嵌入式开发技能(嵌入式工程师必备)
  6. 事件处理-注册时间 // 事件处理-修饰符 // 事件处理-键盘事件的修饰符 // 事件处理-系统修饰符 // 事件处理-鼠标修饰符
  7. 升级dedecms5.5后,出现提示保存目录数据时失败,请检查你的输入资料是否存在问题...
  8. sublime实用快捷键 mac版
  9. atitit.ntfs ext 文件系统新特性对比
  10. 010editor 过期处理
  11. 经典语录(确实经典)
  12. 【日常学习】使用anaconda管理环境并安装cuda和cudnn和tensorflow
  13. TabLayout 的使用 更改下划线的长度,和一个奇葩的问题
  14. 【机器学习】线性回归实战案例一:多元素情况下广告投放效果分析步骤详解
  15. cip核字号验证_cip核字号(cip数据核字号查询官网)
  16. 谷歌地图的简单轨迹移动播放
  17. 子集和问题 算法_LeetCode 题解 | 78.子集
  18. C语言在中math.h中sqrt()函数的使用
  19. Java | 二维数组的初始化
  20. 免费是王道!盘点国外八大知名杀毒软件产品

热门文章

  1. 轨道病害视觉检测:背景、方法与趋势
  2. 香港理工大学人工智能设计实验室 博士后 招聘
  3. 薪资优厚 | 深圳诺博医疗诚聘工程师,实习、全职四个岗位任君选
  4. 文档理解最新技术介绍 | DAS 2020 Keynote Speech
  5. CVPR 2019 神奇的超分辨率算法DPSR:应对图像模糊降质
  6. 3D游戏建模就是那么简单
  7. 收藏 | 深度学习不确定性量化: 技术、应用与挑战
  8. 如何准确估计机器人的状态,增强机器人控制的精度及稳定性
  9. 深度学习(六十四)Faster R-CNN物体检测
  10. Arcgis自动编号实现