【C++ 教程】深入理解单例模式(Singleton Pattern)
在软件开发中,我们经常遇到这样的需求:某个类在系统中只能有一个实例,并且我们希望全局访问它。这时候,**单例模式(Singleton Pattern)**就派上用场了。
✨ 什么是单例模式?
单例模式确保一个类只有一个实例,并提供一个全局访问点来获取这个实例。
适用场景:
- 日志记录器(Logger)
- 配置管理器(ConfigManager)
- 线程池(ThreadPool)
- 数据库连接池(ConnectionPool)
🧱 单例模式的关键要素
一个标准的单例类应该具备以下特点:
- 构造函数私有化:防止外部通过
new创建对象。 - 删除拷贝构造和赋值运算符:防止通过拷贝创建新实例。
- 提供静态方法获取唯一实例:作为全局访问点。
- 线程安全:确保在多线程环境中依然只生成一个实例。
🧪 C++ 单例模式代码实现
#include <iostream>
class Singleton {
public:
static Singleton& getInstance() {
static Singleton instance; // 局部静态变量,首次调用时构造,线程安全
return instance;
}
// 删除拷贝构造函数和赋值运算符,防止复制
Singleton(const Singleton&) = delete;
Singleton& operator=(const Singleton&) = delete;
void doSomething() {
std::cout << "doSomething()" << std::endl;
}
private:
Singleton() {
std::cout << "Singleton()" << std::endl;
}
};
调用
int main(){
Singleton& s1 = Singleton::getInstance(); //外部获取单例的入口
Singleton& s2 = Singleton::getInstance();
s1.doSomething();
if(&s1 == &s2){
std::cout << "s1 和 s2 是同一个实例" << std::endl;
}
}
笔试例题
🧪 C++11 多线程测试 Singleton 构造函数是否只调用一次
📝 题目描述
使用 C++11 的线程库 std::thread,完成以下任务:
- 创建一个线程安全的
Singleton单例类,采用懒加载(局部静态变量方式) - 禁止拷贝构造和赋值操作
- 启动 10 个线程,每个线程都调用
Singleton::getInstance(),并打印实例地址 - 观察输出结果,验证:
- 构造函数是否只执行了一次
- 每个线程拿到的实例地址是否相同
代码模板
请完成以下代码:
#include <iostream>
#include <thread>
#include <vector>
class Singleton {
public:
static Singleton& getInstance() {
// 实现懒加载的线程安全单例
static Singleton instance;
return instance;
}
Singleton(const Singleton&) = delete;
Singleton& operator=(const Singleton&) = delete;
void printAddress() {
std::cout << "Instance address: " << this
<< " | Thread ID: " << std::this_thread::get_id()
<< std::endl;
}
private:
Singleton() {
std::cout << ">>> Constructor called: Singleton()" << std::endl;
}
};
void threadFunc() {
Singleton& s = Singleton::getInstance();
s.printAddress();
}
int main() {
std::vector<std::thread> threads;
// 启动10个线程调用单例
for (int i = 0; i < 10; ++i) {
threads.emplace_back(threadFunc);
}
for (auto& t : threads) {
t.join();
}
return 0;
}
16万+

被折叠的 条评论
为什么被折叠?



