有些类应该保证只有一个对象, 例如:PS界面上的“工具箱”,抽象点的有:负责读取参数的接口、创建对象的接口等。
保证一个类**[1]仅有一个实例, 并提供一个可以访问它的[2]全局访问点**。
- 仅有一个
-
方法一 : 将[*]构造函数声明为私有, 外部不能new新实例了。
-
方法二 : 用noncopyable实现,详细参考:boost/serialization/singleton.hpp
- 全局访问点
-
一般会有: [*](public) static Singleton getInstance()
同时在类内定义:[*](private) static Singleton* p;
[饿汗]在类外直接实例化:Singleton* Singleton::p = new Singleton();
- 要保证多线程安全
要素
- 私有构造方法
- 私有静态引用指向自己的实例
- 以实例为返回值的公有静态方法getInstance
- 活动的单例只有一个实例,并提供了对唯一实例的受控访问
- 只存在一个对象,因此可以节约系统资源,加快对象访问速度
- 避免对共享资源的多重占用
- 不适用于变化的对象
- 单例不存在抽象层,拓展不便
- 单例既要保证自己唯一,又肩负一定职责,一定程度上违背了**“单一职责原则”**
- 滥用会使共享资源庞大而溢出
- 多线程不安全
- 解决这一问题的方案根据实例化的早晚大致可以分为[饱汉法]和[饿汉法],具体的解决方案有五六种。其中**[饱汉法]多以“加锁”来解决,上面的“在类外直接实例化”就是[饿汉法]**的典型实现,代价是牺牲空间。
适合应用于公用场合的对象:
- 需要频繁实例化 然后销毁的对象
- 创建对象消耗的时间/资源过多,但又经常要用到的对象
- 有状态的工具类对象
- 频繁访问数据库或文件的对象
总的来说可以概括为:
- 资源共享的情况下,避免损耗。如日志文件、应用配置
- 控制资源的情况下,方便通信。如线程池