实习工作面试常问的设计模式多种设计模式(单例模式)

【C++ 教程】深入理解单例模式(Singleton Pattern)

在软件开发中,我们经常遇到这样的需求:某个类在系统中只能有一个实例,并且我们希望全局访问它。这时候,**单例模式(Singleton Pattern)**就派上用场了。


✨ 什么是单例模式?

单例模式确保一个类只有一个实例,并提供一个全局访问点来获取这个实例。

适用场景:

  • 日志记录器(Logger)
  • 配置管理器(ConfigManager)
  • 线程池(ThreadPool)
  • 数据库连接池(ConnectionPool)

🧱 单例模式的关键要素

一个标准的单例类应该具备以下特点:

  1. 构造函数私有化:防止外部通过 new 创建对象。
  2. 删除拷贝构造和赋值运算符:防止通过拷贝创建新实例。
  3. 提供静态方法获取唯一实例:作为全局访问点。
  4. 线程安全:确保在多线程环境中依然只生成一个实例。

🧪 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,完成以下任务:

  1. 创建一个线程安全的 Singleton 单例类,采用懒加载(局部静态变量方式)
  2. 禁止拷贝构造和赋值操作
  3. 启动 10 个线程,每个线程都调用 Singleton::getInstance(),并打印实例地址
  4. 观察输出结果,验证:
    • 构造函数是否只执行了一次
    • 每个线程拿到的实例地址是否相同

代码模板

请完成以下代码:

#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;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值