C++单例模式

 C++ 单例模式_c++单例模式-CSDN博客

文章内容来自上面的文章

#include <iostream>
#include "widget.h"
using namespace std;

/*
*	版本1 SingletonPattern_V1 存在以下两个问题
*
*	1. 线程不安全, 非线程安全版本
*	2. 内存泄露
*/

class SingletonPattern_V1
{
private:
    SingletonPattern_V1() {
        cout << "constructor called!" << endl;
    }
    SingletonPattern_V1(SingletonPattern_V1&) = delete;
    SingletonPattern_V1& operator=(const SingletonPattern_V1&) = delete;
    static SingletonPattern_V1* m_pInstance;

public:
    ~SingletonPattern_V1() {
        cout << "destructor called!" << endl;
    }
    //在这里实例化
    static SingletonPattern_V1* Instance() {
        if (!m_pInstance) {
            m_pInstance = new SingletonPattern_V1();
        }
        return m_pInstance;
    }
    void use() const { cout << "in use" << endl; }
};
//在类外初始化静态变量
SingletonPattern_V1* SingletonPattern_V1::m_pInstance = nullptr;

//函数入口
int main(int argc, char *argv[])
{
    //测试
    SingletonPattern_V1* p1 = SingletonPattern_V1::Instance();
    SingletonPattern_V1* p2 = SingletonPattern_V1::Instance();
    p1->use();
    p2->use();
    return 0;
}

constructor called!

in use

in use

容易知道此时是内存泄漏的 

线程安全:

多线程中:

static SingletonPattern_V1* Instance() {
		if (!m_pInstance) {
			m_pInstance = new SingletonPattern_V1();
		}
		return m_pInstance;
	}

执行该段代码时,if(!m_pInstance),如果线程A和线程B都判断为空,都开始初始化实例,那么会初始化两次.此时需要加锁.

解决问题后的代码:

#include <iostream>
using namespace std;
#include <memory> // C++11 shared_ptr头文件
#include <mutex>  // C++11 mutex头文件
/*
*	版本2 SingletonPattern_V2 解决了V1中的问题
*
*	1. 通过加锁让线程安全了
*	2. 通过智能指针(shareptr 基于引用计数)内存没有泄露了
*/
class SingletonPattern_V2 
{
public:
	~SingletonPattern_V2() {
		std::cout << "destructor called!" << std::endl;
	}
	SingletonPattern_V2(SingletonPattern_V2&) = delete;
	SingletonPattern_V2& operator=(const SingletonPattern_V2&) = delete;
 
	//在这里实例化
	static std::shared_ptr<SingletonPattern_V2> Instance() 
	{
		//双重检查锁
		if (m_pInstance == nullptr) {
			std::lock_guard<std::mutex> lk(m_mutex);
			if (m_pInstance == nullptr) {
				m_pInstance = std::shared_ptr<SingletonPattern_V2>(new SingletonPattern_V2());
			}
		}
		return m_pInstance;
	}
 
private:
	SingletonPattern_V2() {
		std::cout << "constructor called!" << std::endl;
	}
	static std::shared_ptr<SingletonPattern_V2> m_pInstance;
	static std::mutex m_mutex;
};
 
//在类外初始化静态变量
std::shared_ptr<SingletonPattern_V2> SingletonPattern_V2::m_pInstance = nullptr;
std::mutex SingletonPattern_V2::m_mutex;
 
int main()
{
	std::shared_ptr<SingletonPattern_V2> p1 = SingletonPattern_V2::Instance();
	std::shared_ptr<SingletonPattern_V2> p2 = SingletonPattern_V2::Instance();
 
	system("pause");
	return 0;
}

用智能共享指针和锁把上面的问题给解决了. 

SingletonPattern_V2(SingletonPattern_V2&) = delete;

C++11中=delete的巧妙用法_= delete-CSDN博客

相关推荐

  1. 模式C#】

    2024-06-09 21:30:02       37 阅读
  2. 模式C++)

    2024-06-09 21:30:02       33 阅读
  3. C++ 模式

    2024-06-09 21:30:02       39 阅读
  4. C++ 模式

    2024-06-09 21:30:02       33 阅读
  5. C# 模式

    2024-06-09 21:30:02       19 阅读
  6. C++模式

    2024-06-09 21:30:02       8 阅读
  7. c++ 模式

    2024-06-09 21:30:02       6 阅读

最近更新

  1. TCP协议是安全的吗?

    2024-06-09 21:30:02       18 阅读
  2. 阿里云服务器执行yum,一直下载docker-ce-stable失败

    2024-06-09 21:30:02       19 阅读
  3. 【Python教程】压缩PDF文件大小

    2024-06-09 21:30:02       18 阅读
  4. 通过文章id递归查询所有评论(xml)

    2024-06-09 21:30:02       20 阅读

热门阅读

  1. 语音合成

    2024-06-09 21:30:02       9 阅读
  2. 单链表的实现

    2024-06-09 21:30:02       9 阅读
  3. Jupyter | 如何在Jupyter应用中添加、删除虚拟环境

    2024-06-09 21:30:02       9 阅读
  4. Apache Doris 2.0.11 版本正式发布

    2024-06-09 21:30:02       9 阅读
  5. IntelliJ IDEA安装

    2024-06-09 21:30:02       7 阅读
  6. OnlyOwner在Solidity中是一个修饰符,TypeError:

    2024-06-09 21:30:02       9 阅读
  7. 【C/C++】C语言实现std::move

    2024-06-09 21:30:02       9 阅读
  8. Search用法Python:深入探索搜索功能的应用与技巧

    2024-06-09 21:30:02       11 阅读
  9. spring框架限制接口是否要登录过才能访问

    2024-06-09 21:30:02       8 阅读
  10. 如何用结构化写好GPT的Prompt提示词

    2024-06-09 21:30:02       12 阅读
  11. DefaultTokenServices源码

    2024-06-09 21:30:02       10 阅读