前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >02.你真的知道线程安全的“单件模式”吗?

02.你真的知道线程安全的“单件模式”吗?

作者头像
悟空聊架构
发布2018-05-18 11:29:47
6260
发布2018-05-18 11:29:47
举报

概述:

  单件模式的类图可以说是所有模式的类图中最简单的,事实上,它的类图上只有一个类。

  尽管从设计的视角来说它很简单,但是实现上还是会遇到相当多的波折。

一、与单件模式的问答

1.单件模式只有一个类,应该是很简单的模式,但是问题似乎不少

答:固然正确地实现单件模式需要一点技巧,但是阅读完这篇文章之后,你已经具备了用正确的方式实现单件模式的能力。当你需要控制实例个数时,还是应当使用单件模式。

2.难道我不能创建一个类,把所有的方法和变量都定义为静态的,把类直接当作一个单件?

  答:如果你的类自给自足,而且不依赖于复杂的初始化,那么你可以这么做。但是,因为静态初始化的控制是在CLR受伤,这么做有可能导致混乱,特别是当有许多类牵涉其中的时候。这么做常常会造成一些微妙的,不容易发现的和初始uade次序有关的bug。除非你有绝对的必要使用类的单件,否则还是建议使用对象的单件

3.类应该做一件事,而且只做一件事。类如果能做两件事,就会被认为是不好的OO设计,单件有没有违反这样的观念?

  答:你说的是“一个类,一个责任”原则。没错,你似的对的,但见类不只负责管理自己的实例,并提供全局访问,还在应用程序中担当角色,所以也可以被视为是两个责任。尽管如此,由类管理自己的实例的做法并不少见。这可以让整体设计更简单。更何况,许多开发人员都已经熟悉了单件模式的这种做法。

4.我想把单件类当成超类,设计出子类,但是我遇到了问题,究竟可以不可以继承单件类?

  答:继承单件类会遇到一个问题,就是构造器是私有的。你不能用私有构造器来扩展类。所以你必须把单件的构造器改成公共的或受保护的。但是这么一来就不算真正的单件了,因为别的类也可以实例化他。

如果你果真把构造器的访问权限改了,还有另一个问题出现,单件的实现是利用静态变量,直接继承会导致所有的派生类共享同一个实例变量,这可能不是你想要的。

5.我还是不了解为何全局变量比单件模式差。

  答:在.net中,全局变量基本上就是对对象的静态引用。在这样的情况下使用全局变量会有一些缺点,我们已经提到了其中的一个:急切实例化VS延迟实例化。但是我们要记住这个模式的目的:确保类只有一个实例并提供全局访问,但是不能确保只有一个实例。全局变量也会变相鼓励开发人员,用许多全局变量指向许多小对象来造成这样的现象,但单件仍然可能被滥用。

二、垃圾回收

如果没有一个全局变量引用单件模式的实例,该实例是否会被垃圾回收?

经过自己写代码的验证:不会被回收。

由下面的结果可知,两次调用GetInstance,只创建了一次Singleton实例

三、职责:

  1.保证一个类有且仅有一个实例

  2.且提供一个全局访问点

四、代码中需要用到的地方

  线程池(Thread Pool)/缓存(cache)/对话框/处理偏好设置和注册表的对象/日志对象/充当打印机/显卡等设备的驱动程序的对象。

五、生活中用到的地方

  1.考勤记录仪可以有多台,但是时钟必须只有一个,所有的考勤记录必须根据这个时钟来生成打卡时间记录。且该时钟是唯一的时间访问入口。

  2.足球场上只能根据主裁判的手表来判断比赛进行了多长时间,比赛进行的时间是唯一的,

查看比赛进行的时间的访问入口时主裁判的手表上的时间。

六、对比全局静态变量

我们可以用全局静态变量指向一个对象。程序员工作的时候约定好,只用这个全局变量作为唯一的一个访问这个对象的入口。

优点:

  1.代码定义简单

  2.调用方便

缺点:

  1.程序员之间需要约定

  2.程序一开始就得创建好对象,如果该对象非常耗资源,而程序执行的过程中又一直没有用到它,就形成了资源的浪费。

  3.不能保证一个对象只能被实例化一次,如果程序员之间的约定并没有严格遵守,比如新来的同事并不知道有这个约定。

七、原理图:

Singleton

Static uniqueInstance //其他有用的单件数据...

Static GetInstance()

//其他有用的单件方法...

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2015-11-09 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、与单件模式的问答
    • 1.单件模式只有一个类,应该是很简单的模式,但是问题似乎不少
      • 2.难道我不能创建一个类,把所有的方法和变量都定义为静态的,把类直接当作一个单件?
        • 3.类应该做一件事,而且只做一件事。类如果能做两件事,就会被认为是不好的OO设计,单件有没有违反这样的观念?
          • 4.我想把单件类当成超类,设计出子类,但是我遇到了问题,究竟可以不可以继承单件类?
            • 5.我还是不了解为何全局变量比单件模式差。
            • 二、垃圾回收
            • 三、职责:
            • 四、代码中需要用到的地方
            • 五、生活中用到的地方
            • 六、对比全局静态变量
            • 七、原理图:
            领券
            问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档