单例模式

定义:

要求一个类只能生成一个对象,所有对象对它的依赖相同。

优点:

  1. 只有一个实例,减少内存开支。应用在一个经常被访问的对象上
  2. 减少系统的性能开销,应用启动时,直接产生一单例对象,用永久驻留内存的方式。
  3. 避免对资源的多重占用
  4. 可在系统设置全局的访问点,优化和共享资源访问。

缺点:

  1. 一般没有接口,扩展困难。原因:接口对单例模式没有任何意义;
  2. 单例模式对测试是不利的。如果单例模式没完成,是不能进行测试的。
  3. 单例模式与单一职责原则有冲突。原因:一个类应该只实现一个逻辑,而不关心它是否是单例,是不是要单例取决于环境;单例模式把“要单例”和业务逻辑融合在一个类。

使用场景:

  1. 内存消耗大的
  2. 硬件
#include <iostream>
#include <thread>
#include <mutex>


std::mutex mtx;

//法一:懒汉式单例(线程不安全)
//线程不安全,当几个线程同时执行到语句if (singleton == nullptr)时,singleton都还没有被创建,所以就重复创建了几个实例。
//可以通过在getSingelton中加锁来实现
#if 0
class Singleton
{
private:
	static Singleton *singleton;

public:
	inline static Singleton *getSingleton()
	{
		if (singleton == nullptr)
		{
			singleton = new Singleton();
		}

		return singleton;
	}
};
#endif

//法二:懒汉式单例(线程安全)
//在getSingelton中加锁来实现
//但是这种情况会在调用getSingleton的时候每次都加锁,耽误时间
//可以再if (singleton == nullptr)中加锁
#if 0
std::mutex single_mtx;

class Singleton
{
public:
	inline static Singleton* getSingleton()
	{
		std::unique_lock<std::mutex> single_lock(single_mtx);
		if (singleton == nullptr)
		{
			singleton = new Singleton();
		}

		return singleton;
	}
	private:
		static Singleton* singleton;
};
#endif


std::mutex single_mtx;

class Singleton
{
public:
	inline static Singleton* getSingleton()
	{
		if (singleton == nullptr)
		{
			//单独在这加的话会出现多个线程都满足singleton == nullptr,然后进入到这的情况。故需要在下面再次判断一次singleton == nullptr,然后创建对象
			std::unique_lock<std::mutex> single_lock(single_mtx);
			if (singleton == nullptr)//双重判断保证线程安全
			{
				singleton = new Singleton();
			}
		}

		return singleton;
	}
private:
	static Singleton* singleton;
};

Singleton *Singleton::singleton = nullptr;

void printAddr()
{
	std::unique_lock<std::mutex> lock(mtx);
	Singleton *singleton = Singleton::getSingleton();
	std::cout << singleton << std::endl;
}

int main()
{
	std::thread threads[5];

	for (auto &t : threads)
		t = std::thread(printAddr);

	for (auto &t : threads)
		t.join();
	return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值