.NET设计模式(1):1.1 单例模式(Singleton Pattern)
概述
单例模式就是保证在整个应用程序的生命周期中,在任何时刻,被指定的类只有一个实例,并为客户程序提供一个获取该实例的全局访问点。
单例模式是一种常用的软件设计模式。在它的核心结构中只包含一个被称为单例的特殊类。通过单例模式可以保证系统中一个类只有一个实例而且该实例易于外界访问,从而方便对实例个数的控制并节约系统资源。如果希望在系统中某个类的对象只能存在一个,单例模式是最好的解决方案。
意图
保证一个类仅有一个实例,并提供一个该实例的全局访问点。
场景
- Windows的Task Manager(任务管理器)就是很典型的单例模式,任何时候只能打开一个窗口。
- windows的Recycle Bin(回收站)也是典型的单例应用。在整个系统运行过程中,回收站一直维护着仅有的一个实例。
- 网站的计数器,一般也是采用单例模式实现,否则难以同步。
- 应用程序的日志应用,一般都何用单例模式实现,这一般是由于共享的日志文件一直处于打开状态,因为只能有一个实例去操作,否则内容不好追加。
- Web应用的配置对象的读取,一般也应用单例模式,这个是由于配置文件是共享的资源。
- 数据库连接池的设计一般也是采用单例模式,因为数据库连接是一种数据库资源。数据库软件系统中使用数据库连接池,主要是节省打开或者关闭数据库连接所引起的效率损耗,这种效率上的损耗还是非常昂贵的,因为何用单例模式来维护,就可以大大降低这种损耗。
- 多线程的线程池的设计一般也是采用单例模式,这是由于线程池要方便对池中的线程进行控制。
- 操作系统的文件系统,也是大的单例模式实现的具体例子,一个操作系统只能有一个文件系统。
- HttpApplication 也是单位例的典型应用。熟悉ASP.Net(IIS)的整个请求生命周期的人应该知道HttpApplication也是单例模式,所有的HttpModule都共享一个HttpApplication实例.
实现
1.将该类的构造方法定义为私有方法,这样其他处的代码就无法通过调用该类的构造方法来实例化该类的对象,只有通过该类提供的静态方法来得到该类的唯一实例;
2.在该类内提供一个静态方法,当我们调用这个方法时,如果类持有的引用不为空就返回这个引用,如果类保持的引用为空就创建该类的实例并将实例的引用赋予该类保持的引用。
饿汉式
- 静态常量(经典写法)
public class Singleton
{
private static Singleton _instance = new Singleton();
private Singleton() { }
public static Singleton Instance()
{
return _instance;
}
}
适用:单/多线程
模式:饿汉式(静态常量)[可用]
优点:写法比较简单,避免了线程同步问题
缺点:没能实现延迟加载
- 静态代码块
public class Singleton2
{
private static Singleton2 _instance;
static Singleton2()
{
_instance = new Singleton2();
}
private Singleton2(){}
public Singleton2 Instance()
{
return _instance;
}
}
适用:单/多线程
模式:饿汉式(静态代码块)[可用]
优点:写法比较简单,避免了线程同步问题
缺点:没能实现延迟加载
懒汉式
- 线程不安全
public class Singleton3
{
private static Singleton3 _instance;
private Singleton3() { }
public static Singleton3 Instance()
{
return _instance ?? (_instance = new Singleton3());
}
}
适用:单线程
模式:懒汉式(线程不安全)[不可用]
优点:适用于单线程,实现简单,延迟加载
缺点:多线程不安全,违背了单列模式的原则
- 线程不安全
public class Singleton4
{
private static Singleton4 _instance;
private static readonly object SyncObject = new object();
private Singleton4() { }
public static Singleton4 Instance()
{
lock (SyncObject)
{
if (_instance == null)
{
_instance = new Singleton4();
}
}
return _instance;
}
}
适用:单线程
模式:懒汉式(线程安全)[不推荐]
优点:线程安全;延迟加载;
缺点:这种实现方式增加了额外的开销,损失了性能(当有多个调用时,第一个调用的会进入lock,而其他的则等待第一个结束后才能调用,后面的依次访问、等待……)
- 双重检查锁定
public class Singleton5
{
private static Singleton5 _instance;
private static readonly object SyncObject = new object();
private Singleton5() { }
public static Singleton5 Instance()
{
if (_instance==null)
{
lock (SyncObject)
{
if (_instance == null)
{
_instance = new Singleton5();
}
}
}
return _instance;
}
}
适用:单/多线程
模式:双重检查锁定(Double-Check Locking)(线程安全)[推荐]
优点:线程安全;延迟加载;效率较高(只会实例化一次,首先会判断是否实例化过,如果实例化了,直接返回实例,不需要进入lock;如果未实例化,进入lock,就算是多个调用也无妨,第一次调用的会实例化,第二个进入lock时会再次判断是否实例化,这样线程就不会阻塞了。)
缺点:基本没有
- 静态内部类
public class Singleton6
{
private Singleton6() { }
private static class SingletonInstance
{
public static Singleton6 Instance = new Singleton6();
}
public static Singleton6 Instance()
{
return SingletonInstance.Instance;
}
}
适用:单/多线程
模式:静态内部类(线程安全)[推荐]
优点:避免了线程不安全;延迟加载;效率高(这种方式跟饿汉式方式采用的机制类似:都是采用了类装载的机制来保证初始化实例时只有一个线程。不同的地方是:饿汉式只要Singleton类被装载就会实例化,没有Lazy-Loading的作用;而静态内部类方式在Singleton类被装载时并不会立即实例化,而是在需要实例化时,调用Instance方法,才会装载SingletonInstance类,从而完成Singleton的实例化。)
缺点:基本没有
.NET设计模式(1):1.1 单例模式(Singleton Pattern)的更多相关文章
- 深入设计模式(二)——单例模式(Singleton Pattern)
一.单例模式介绍 单例模式(Singleton Pattern),保证一个类只有一个实例,并提供一个访问它的全局访问点.单例模式因为Singleton封装它的唯一实例,它就可以严格地控制客户怎样访问它 ...
- 浅谈设计模式--单例模式(Singleton Pattern)
题外话:好久没写blog,做知识归纳整理了.本来设计模式就是个坑,各种文章也写烂了.不过,不是自己写的东西,缺少点知识的存在感.目前还没做到光看即能记住,得写.所以准备跳入设计模式这个大坑. 开篇先贡 ...
- 设计模式之单例模式(Singleton Pattern)
单例模式 单例模式(Singleton Pattern)在java中算是最常用的设计模式之一,主要用于控制控制类实例的数量,防止外部实例化或者修改.单例模式在某些场景下可以提高系统运行效率.实现中的主 ...
- 乐在其中设计模式(C#) - 单例模式(Singleton Pattern)
原文:乐在其中设计模式(C#) - 单例模式(Singleton Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 单例模式(Singleton Pattern) 作者:weba ...
- 设计模式系列之单例模式(Singleton Pattern)——确保对象的唯一性
模式概述 模式定义 模式结构图 饿汉式单例与懒汉式单例 饿汉式单例 懒汉式单例 模式应用 模式在JDK中的应用 模式在开源项目中的应用 模式总结 主要优点 适用场景 说明:设计模式系列文章是读刘伟所著 ...
- 【设计模式】单例模式 Singleton Pattern
通常我们在写程序的时候会碰到一个类只允许在整个系统中只存在一个实例(Instance) 的情况, 比如说我们想做一计数器,统计某些接口调用的次数,通常我们的数据库连接也是只期望有一个实例.Windo ...
- 二十四种设计模式:单例模式(Singleton Pattern)
单例模式(Singleton Pattern) 介绍保证一个类仅有一个实例,并提供一个访问它的全局访问点. 示例保证一个类仅有一个实例. Singleton using System; using S ...
- 抽象工厂(Abstract Factory),工厂方法(Factory Method),单例模式(Singleton Pattern)
在谈工厂之前,先阐述一个观点:那就是在实际程序设计中,为了设计灵活的多态代码,代码中尽量不使用new去实例化一个对象,那么不使用new去实例化对象,剩下可用的方法就可以选择使用工厂方法,原型复制等去实 ...
- Net设计模式实例之单例模式( Singleton Pattern)
一.单例模式简介(Brief Introduction) 单例模式(Singleton Pattern),保证一个类只有一个实例,并提供一个访问它的全局访问点.单例模式因为Singleton封装它的唯 ...
随机推荐
- C#_闭包陷阱
如果匿名方法(Lambda表达式)引用了某个局部变量,编译器就会自动将该引用提升到该闭包对象中. 即将for循环中的变量i修改成了引用闭包对象的公共变量i.这样一来,即使代码执行后离开了原局部变量i的 ...
- LVS DR模式 RealServer 为 Windows 2008 R2配置
有3篇文档详细介绍 http://kb.linuxvirtualserver.org/wiki/Windows_Servers_in_LVS/DR_and_LVS/TUN_Clusters http: ...
- 嵌入式的重要平台 .NET Micro Framework
曾经辉煌的巨人PC界渐渐走向下坡路,而智能手机圈则没完没了般地争个你死我活.随着智能手机的广泛普及,不少商家为了不坐以待毙而纷纷开始涉足与穿戴式设备--智能手表(具体参见智能手表时代还有多远). 我们 ...
- ABP理论学习之日志记录
返回总目录 本篇目录 服务端 获取Logger 基类中的Logger 配置 客户端 服务端 ABP使用的是Castle Windsor的日志记录设备.它可以和不同的日志类库一起工作,比如Log4Net ...
- 一个App完成入门篇(六)- 完成通讯录页面
第五章和第六章间隔时间有点长,对不起大家了.下面继续. 本节教程将要教会大家如何加载本地通讯录. 导入项目 导入通讯录 自定义js模块 发送和订阅page消息 将要学习的demo效果图如下所示 1. ...
- Step by Step 创建一个新的Dynamics CRM Organization
原创地址:http://www.cnblogs.com/jfzhu/p/4012833.html 转载请注明出处 前面演示过如何安装Dynamics CRM 2013,参见<Step by st ...
- EF:Oracle.DataAccess.Client.OracleException: ORA-12154: TNS:could not resolve the connect identifier specified
报告错误:Oracle.DataAccess.Client.OracleException: ORA-12154: TNS:could not resolve the connect identifi ...
- MySql.Data.MySqlClient.MySqlException: Parameter ‘@maxid’ must be defined
本文涉及到的mysql知识点: mysql中的if条件语句用法: IF(expr1,expr2,expr3) mysql使用变量(mysql中变量不用事前申明) mysql事务 testcase 为了 ...
- PHP fsockopen 异步调用接口在nginx上偶尔实效的情况
private function fsock_asy_do($get){ $fp = fsockopen("ssl://www.xxx.com", 443, $errno, $er ...
- Sql Server系列:视图
视图是数据库中的一种虚拟表,与真实的表一样,视图包含一系列带有名称的行和列数据.行和列数据用来自定义视图的查询所引用的表,并且在引用视图时动态生成. 1. 视图的概念 视图是从一个或者多个表中导出的, ...