2.面向对象设计模式学习之Singleton单件模式
Singleton单件(创建型模式)
1、动机(应用场景):
在软件系统中,必须保证系统中只存在一个实例,才能确保逻辑正确性和良好的效率。
2、意图:
保证一个类仅有一个实例,并提供全局访问点。
3、实现:
有的人可能会觉得,要保证一个系统中一个类只能有一个实例,那么这个类和平常一样写,然后你在系统中只实例化一次不就得了?
其实这应该是类的设计者的责任还,而不是类的使用者的责任。
1)单线程下Singleton单件模式的实现:
单线程下Singleton单件模式实现的主要有两个步骤。
第一是构造器加上static静态字段,防止使用止使用的时候实例化;
第二是取得对象值的时候,判断对象是否已经存在(是否为null),如果存在,则无需实例化,直接返回对象的成员,如果不存在,则实例化。
/// <summary> /// 单线程下 Singleton 单件模式 例子 ///[ZengWenZhi] 2012-8-3创建 /// </summary> public class Singleton { private static Singleton instance; //私有构造器,防止被 new。
private Singleton() { } public static Singleton Instance { get { if (instance==null) { instance = new Singleton(); } return instance; } } }
2)多线程下Singleton单件模式的实现:
多线程下单件模式的关键技术是lock技术。如下代码所示,在多线程环境下,可能两个线程同时运行到A点(A\B点一下代码有标注),这样两个线程都会判断到instance对象为空,这样,两个线程都会运行到B点。假如没有B点的代码,就会创建两个instance对象,有了B点的代码就可以避免这个问题。
/// <summary> /// 多线程下 Singleton 单件模式 例子 ///[ZengWenZhi] 2012-8-3创建 /// </summary> public class SingletonM { //volatile 当一个变量定义为volatile时,读取这个变量的值时候每次都是从momery里面读取而不是从cache读。
//这样做是为了保证读取该变量的信息都是最新的,而无论其他线程如何更新这个变量 private static volatile SingletonM instance = null; private static object lockHelper = new object(); private SingletonM() { } public static SingletonM Instance { get { if (instance==null)//A点 { lock (lockHelper)//B点 { //双检查 预防代码编译的时候作出优化调整了代码执行顺序 if (instance==null) { instance = new SingletonM(); } } } return instance; } } }
3、.net框架下Singleton单件模式的身影:
/// <summary> /// Singleton 单件模式实例 ///[ZengWenZhi] 2012-8-3创建 /// </summary> class Program { static void Main(string[] args) { //.Net框架中的应用 MyClass class1 = new MyClass(); MyClass calss2 = new MyClass(); Type type1 = class1.GetType(); Type type2 = class1.GetType(); //发现两个输出是一样的,这说明全局中只有一个MyClass 的type对象。 Console.WriteLine(type1.ToString()); Console.WriteLine(type2.ToString()); Console.ReadLine(); } } //应用 class MyClass { }
重要声明:本文是笔者学习李建中老师的时候所记录笔记,里面知识并非原创。
分类:
面向对象设计模式
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?