C# 创建单例你会几种方式?
关于为什么需要创建单例?这里不过多介绍,具体百度知。
关于C# 创建单例步骤或条件吧
1、声明静态变量;2、私有构造函数(无法实例化)3、静态创建实例的方法;至于我这里的Singleton是sealed ,只是为了防止被继承,其实有私有构造函数足够了,这里只是为了代码可读性。
第一种常见的方式创建单例:
/// <summary>
/// 不安全的单例
/// </summary>
public sealed class Singleton
{
private static Singleton _Singleton;
private Singleton() { }
public static Singleton GetSingleton()
{
if (_Singleton == null)
{
_Singleton = new Singleton();
}
return _Singleton;
}
}
注:为什么说是不安全的单例,多线程访问时可能会new多个对象...
第二种方式创建单例:
/// <summary>
/// (多线程)安全单例
/// </summary>
public sealed class Singleton
{
private static Singleton _Singleton;
private static readonly object obj = new object();
private Singleton() { }
public static Singleton GetSingleton()
{
if (_Singleton == null)
{
//加锁保护,在多线程下可以确保实例值被创建一次。缺点是每 次获取单例,都要进行判断,涉及到的锁和解锁比较耗资源。
lock (obj)
{
if (_Singleton == null)
{
_Singleton = new Singleton();
}
} }
return _Singleton;
}
}
注:为了解决上面第一种方式创建的不安全实例问题应用而生。
第三种方式创建单例:
/// <summary>
/// 只读单例
/// </summary>
public sealed class Singleton
{
private static readonly Singleton instance = new Singleton();
private Singleton() { }
public static Singleton Instance
{
get
{
return instance;
}
}
}
/// <summary>
/// 基于上面的只读单例=自动属性只读单例(语法糖)
/// </summary>
public sealed class Singleton
{
private Singleton() { }
public static Singleton Instance { get; } = new Singleton();
}
注:只读属性式=>借助readonly属性,instance只被初始化一次,同样达到了单例的效果。在引用函数执行第一句话之前,instance其实已经被赋值了,并不是预期的 只有到访问Instance变量时才创建对象。
第四种方式创建单例:
/// <summary>
/// Singleton中加上静态构造函数。
/// </summary>
public sealed class Singleton
{
public static readonly Singleton instance = new Singleton();
private Singleton()
{
Console.WriteLine("初始化1!");
}
static Singleton()
{
}
public static Singleton Instance
{
get { return instance; }
}
}
注:为了解决(第三种只读属性实例)在执行第一句代码之前,实例已经被初始化问题。
第五种方式创建单例:
/// <summary>
/// 使用Lazy创建单例,默认是线程安全的
/// </summary>
public sealed class Singleton
{
private static readonly Lazy<Singleton> instance = new Lazy<Singleton>(() => new Singleton());//
private Singleton() { }
public static Singleton Instance
{
get
{
return instance.Value;
}
}
}
// 贴一下关于上面Lazy<T> s=new Lazy<T>()参数的定义;
// 摘要:
// 初始化System.Lazy`1类的新实例。 懒惰初始化时
// 发生时,使用指定的初始化函数和初始化模式。 // 参数:
// valueFactory:
// 被调用以生成延迟初始化值的委托是必需的参数
//
// isThreadSafe:
// 如果要使此实例可由多个线程同时使用,则为true; false
//使此实例一次只能由一个线程使用。
public Lazy(Func<T> valueFactory, bool isThreadSafe);
C# 创建单例你会几种方式?的更多相关文章
- iOS:创建单例对象的两种方式
单例模式:创建单例对象的两种方式 方式一:iOS4版本之前 static SingleClassManager *singleManager = nil; +(SingleClas ...
- Java中 单例(Singleton)的两种方式
第一种(饿汉式单例模式):在声明变量时实例化 public class Singleton { //静态初始化自动实例化 private static Singleton instance = new ...
- iOS 创建单例的两种方法
创建一个单例很多办法.我先列举一个苹果官方文档中的写法. [cpp] view plaincopy static AccountManager *DefaultManager = nil; + (Ac ...
- 【iOS开发】创建单例的两种方法
创建一个单例很多办法.我先列举一个苹果官方文档中的写法. [cpp] view plaincopy static AccountManager *DefaultManager = nil; + ( ...
- Spring IOC 容器源码分析 - 创建单例 bean 的过程
1. 简介 在上一篇文章中,我比较详细的分析了获取 bean 的方法,也就是getBean(String)的实现逻辑.对于已实例化好的单例 bean,getBean(String) 方法并不会再一次去 ...
- Spring使用facotry-method创建单例Bean总结<转>
阅读目录 1 最原始的实现单例模式的方法(存在线程不安全): 2 通过关键字Synchronized强制线程同步 3 通过静态内部类进行单例 通过spring的factory-method来创建 ...
- 【Spring实战】—— 3 使用facotry-method创建单例Bean总结
如果有这样的需求: 1 不想再bean.xml加载的时候实例化bean,而是想把加载bean.xml与实例化对象分离. 2 实现单例的bean 以上的情况,都可以通过工厂方法factory-metho ...
- [iOS dispatch_once创建单例]
自苹果引入了Grand Central Dispatch (GCD)(Mac OS 10.6和iOS4.0)后,创建单例又有了新的方法,那就是使用dispatch_once函数,当然,随着演进的进行, ...
- Swift - 代码创建单例
创建单例的方法 import UIKit //创建一个单例类 class SingleInstance: NSObject { //在单例类中,有一个用来共享数据的数组 var datas = [St ...
随机推荐
- DHCP中继器
DHCP客户机和服务器在不同的子网内,客户机向服务器申请IP地址,这就要用到DHCP中继代理.DHCP中继代理实际上是一种软件技术,安装了DHCP中继代理的计算机称为DHCP中继代理服务器,它承担不同 ...
- maven项目编译:程序包com.sun.image.codec.jpeg不存在 这个类文件的位置在jre/lib/rt.jar
转载:http://superich2008.iteye.com/blog/2047830 失败提示信息为:程序包com.sun.image.codec.jpeg不存在 这个类文件的位置在jre/li ...
- JQ实现小火箭效果
点击返回顶部以动画方式返回 $(function(){ $(window).scroll(function(){ //当滚动距离超过50后,显示按钮: ...
- C++ 函数模板二(函数模板重载)
//函数模板重载 #include<iostream> using namespace std; /* 函数模板会进行严格的类型匹配,模板类型不提供隐式类型转化 普通函数能够进行自动类型转 ...
- mac上制作u盘启动盘
Mac上制作Ubuntu USB启动盘 一.下载ubuntu iso镜像 二.将iso转换为img文件 $ hdiutil convert -format UDRW -o /path/to/gener ...
- 【BZOJ】1857: [Scoi2010]传送带(三分)
http://www.lydsy.com/JudgeOnline/problem.php?id=1857 好神奇的三分.. 第一次写三分啊sad..看了题解啊题解QAQ 首先发现无论怎么走一定是在AB ...
- hdu 4568(SPFA预处理+TSP)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4568 思路:先用spfa预处理出宝藏与宝藏之间的最短距离,宝藏到边界的最短距离,然后就是经典的求TSP ...
- Java中带包的类的编译与执行
http://blog.csdn.net/wbrs13/article/details/4859880
- 67、Fragment实现Tab
<LinearLayout .......... <FrameLayout android:id="@+id/id_content" android:layout_wi ...
- jeesite学习笔记(一) 项目框架
JeeSite是基于多个优秀的开源项目,高度整合封装而成的高效,高性能,强安全性的开源Java EE快速开发平台. 在github上,对jeesite平台有详细的介绍,这里稍作整理,给出项目的内置功能 ...