单例模式:从基础实现到高级应用

单例模式:从基础实现到高级应用

单例模式的核心思想

目的:去报一个类仅有一个实例,并提供全局访问点。

适用场景:

  1. 需要严格控制资源访问(如数据库连接池);
  2. 频繁的创建销毁对象成本高(如配置管理器);
  3. 共享状态管理(如全局计数器);

2种经典实现方式及对比

  1. 饿汉式(线程安全)
c++ 复制代码
class Singleton 
{
priveate:
	static Singleton instance;   //类加载时初始化
	Singleton() = default;	//私有构造函数
	~Singleton() = default;
public:
	static Singleton* getSingleton() 
	{
		return &instance;
	}
	
	Singleton(const Singleton&) = delete;
	Singleton& operator=(const Singleton&) = delete;
}

//初始化静态成员
Singleton Singleton::instance;

特点:

  • 线程安全
  • 可能造成资源浪费(即使不用也会初始化)
  1. 懒汉式(非线程安全)
c++ 复制代码
class Singleton
{
private: 
	static Singleton* instance;   //静态实例指针
	Singleton() = default;		//私有构造函数
	~Singleton() = default;
public:
	static Singleton* getInstance() 
	{
		if (instance == NULL)			//线程不安全点
		{
			instance = new Singleton();
		}
		return instance;
	}
	
	//删除拷贝构造和复制构造操作
	Singleton(const Singleton&) = delete;
	Singleton& operator=(const Singleton&) = delete;
};

问题:多线程下可能创建多个实例

  1. meyer's singleton(C++最佳实践)
c++ 复制代码
class Singleton
{
public:
	static Singleton& getIntance() 
	{
		static Singleton instance;		//C++11保证线程安全
		return instance;	
	}
private:
	Singleton() = default;
	~Singleton() = default;	
};

单例模式的潜在问题与解决方案

1. 防止反射/克隆破化单例

c++ 复制代码
clasee Singleton
{
	//...其他代码...
private:
	//防止通过反射构造
	Singleton() 
	{
		if (instance != NULL)
		{
			throw std::runtime_error("Singleton already exists!");
		}
	}
};

2.处理析构问题

c++ 复制代码
//方案1:智能指针自动管理
static std::shared_ptr<Singleton> getInstance() {
	static std::shared_ptr<Singleton> instance(new Singleton());
	return instance;
}

//方案2:显示释放接口
static void destoryInstance() {
	delete instance;  //需要配合线程安全处理
}

3. 继承单例基类

c++ 复制代码
template<typedef T>
class Singleton {
projected:
	Singleton() = default;
	~Singleton() = default;
public:
	static T& getSingleton() {
		static T instance;
		return instance;
	}

	Singleton(const Singleton&) = delete;
	Singleton& operator=(const Singleton&) = delete;
};

//使用示例
class MyClass : public Singletong<MyClass> {
	friend class Singleton<MyClass>;
private:
	MyClass() = default;
}

单例模式在工程中的实际应用

1. 日志系统

c++ 复制代码
class Logger : public Singleton<Logger> {
public:
    void log(const std::string& message) {
        std::lock_guard<std::mutex> lock(mutex);
        std::cout << "[LOG] " << message << std::endl;
    }

private:
    std::mutex mutex;
    friend class Singleton<Logger>;
    Logger() = default;
};

// 使用
Logger::getInstance().log("System started");

2. 数据库连接池

c++ 复制代码
class ConnectionPool : public Singleton<ConnectionPool> {
public:
    Connection* getConnection() { /*...*/ }
    void releaseConnection(Connection* conn) { /*...*/ }

private:
    std::vector<Connection*> pool;
    friend class Singleton<ConnectionPool>;
    ConnectionPool() { /* 初始化连接池 */ }
};

最终实现推荐

c++ 复制代码
class MySingleton {
public:
    static MySingleton& getInstance() {
        static MySingleton instance;
        return instance;
    }

    // 禁用拷贝和移动
    MySingleton(const MySingleton&) = delete;
    MySingleton& operator=(const MySingleton&) = delete;
    MySingleton(MySingleton&&) = delete;
    MySingleton& operator=(MySingleton&&) = delete;

private:
    MySingleton() = default;  // 私有构造
    ~MySingleton() = default;
};
相关推荐
扫地的小何尚6 小时前
NVIDIA RTX PC开源AI工具升级:加速LLM和扩散模型的性能革命
人工智能·python·算法·开源·nvidia·1024程序员节
数据皮皮侠AI1 天前
上市公司股票名称相似度(1990-2025)
大数据·人工智能·笔记·区块链·能源·1024程序员节
开开心心就好2 天前
系统清理工具清理缓存日志,启动卸载管理
linux·运维·服务器·神经网络·cnn·pdf·1024程序员节
Evan东少4 天前
[踩坑]笔记本Ubuntu20.04+NvidiaRTX5060驱动+cuda+Pytorch+ROS/Python实现人脸追踪(环境准备)
1024程序员节
不爱编程的小陈6 天前
C/C++每日面试题
面试·职场和发展·1024程序员节
开开心心就好6 天前
右键菜单管理工具,添加程序自定义名称位置
linux·运维·服务器·ci/cd·docker·pdf·1024程序员节
码农三叔7 天前
(4-2-05)Python SDK仓库:MCP服务器端(5)Streamable HTTP传输+Streamable HTTP传输
开发语言·python·http·大模型·1024程序员节·mcp·mcp sdk
西幻凌云11 天前
初始——正则表达式
c++·正则表达式·1024程序员节
启芯硬件11 天前
电源XL6009E1的dieshot细节分析-芯片设计干货
大数据·经验分享·硬件工程·1024程序员节
一颗青果13 天前
单例模式 | 死锁
linux·服务器·单例模式·1024程序员节