单例模式(Singleton)
单例模式(Singleton)简介:
单例模式保证一个类仅有一个实例,并提供一个访问它的全局访问点。使用单例模式能够让设计师快速获取提供某项服务或者功能的对象,可以省去层层传递对象的困扰。
单例模式在实现时,需要编程语言的支持,需要编程语言具有静态类属性、静态类方法以及可重新定义构造函数的访问修饰符,具有这3项语句功能的编程语言就可以实现单例模式。
C++代码
单线程
Singleton单例类:
//file: Singleton.h
#pragma once
class Singleton
{
public:
virtual ~Singleton();
static Singleton * getInstance();
void operation();
private:
static Singleton * instance;
Singleton();
};
//file: Singleton.cpp
#include "pch.h"
#include "Singleton.h"
#include <iostream>
Singleton * Singleton::instance = nullptr;
Singleton::Singleton() {}
Singleton::~Singleton()
{
delete instance;
}
Singleton * Singleton::getInstance()
{
if (instance == nullptr)
instance = new Singleton();
return instance;
}
void Singleton::operation()
{
std::cout << "Singleton Operation ." << std::endl;
}
客户端代码:
//file: SingletonPattern.cpp : This file contains the 'main' function. Program execution begins and ends there.
#include "pch.h"
#include "Singleton.h"
#include <iostream>
using namespace std;
int main()
{
Singleton * singleton = Singleton::getInstance();
singleton->operation();
char c;
cin >> c;
return 0;
}
多线程
C#代码
C#单线程
Singleton单例类:
public class Singleton
{
private Singleton() { }
private static Singleton instance = null;
public static Singleton Instance
{
get
{
if (instance == null)
instance = new Singleton();
return instance;
}
}
public void Operation()
{
Console.WriteLine("The Singleton Operation .");
}
}
其中静态类方法Instance用来获取_instance属性,上方代码使用了C#的getter存取运算符功能来实现Instance方法,使Singleton.Instance()的调用方式,写为Singleton.Instance的方式,减少的一对括号对于后续代码维护有着一定程度的帮助。
客户端测试代码:
class Program
{
static void Main(string[] args)
{
Singleton singleton = Singleton.Instance;
singleton.Operation();
Console.ReadKey();
}
}
或者使用方法方式获取单例:
public class Singleton
{
private Singleton() { }
private static Singleton instance = null;
public static Singleton GetInstance()
{
if (instance == null)
{
instance = new Singleton();
}
return instance;
}
public void Operation()
{
Console.WriteLine("The Singleton Operation .");
}
}
//使用时:
//Singleton singleton = Singleton.GetInstance();
C#多线程
public class Singleton
{
private Singleton() { }
private static Singleton instance = null;
private static readonly object syncObj = new object();
public static Singleton Instance
{
////可以在多线程上工作但是效率不高
//get {
// lock (syncObj) {
// if (instance == null)
// instance = new Singleton();
// }
// return instance;
//}
//加同步锁前后两次判断,仅当instance为空时,才进行加锁操作
get {
if (instance == null) {
lock (syncObj) {
if (instance == null)
instance = new Singleton();
}
}
return instance;
}
}
public void Operation()
{
Console.WriteLine("The Singleton Operation .");
}
}
C#多线程单例的另一种写法,这样写虽然很简洁,但是其instance实例并不是在第一次使用的时候才创建,而是在运行时第一次发现Singleton类被用到时就创建了
public class Singleton {
private Singleton() { }
private static Singleton instance = new Singleton();
public static Singleton Instance {
get {
return instance;
}
}
public void Operation()
{
Console.WriteLine("The Singleton Operation .");
}
}
单例模式优点及缺点
优点:
单例模式通过将类的构造方法私有化,让类对象只能够在类的成员方法中产生,配合类的静态成员属性在类中只会出现一个的限制,让系统可以有效的限制数量,因此,单例模式可以有效的限制类对象产生的地点和时间,同时也可以防止类对象被随意产生而造成系统错误。
缺点:
单例模式使用方便,但是在挑选适合以单例模式实现的类时,需要认真挑选,不能够滥用单例;其次,单例模式违反了“开闭原则”,因为通过Instance方法获取的对象是“实现类”不是“接口类”,该方法返回的对象是包含了实现细节的实体类,当后续设计变更后者需求改变时,程序员无法将它替代为其他类,只能改变实现类中原有的程序代码,无法满足“对修改关闭”的要求。
REF
书籍:
设计模式与游戏开发、大话设计模式
GitHub: