qt单例模式

本文介绍了Qt中单例模式的运用,详细解析了单例模式的作用,如减少内存开销和避免资源多重占用。并探讨了两种实现方法:懒汉模式和饿汉模式。懒汉模式在首次请求时创建对象,而饿汉模式在类加载时即创建对象。对于懒汉模式,还讨论了线程安全的实现方式——双检锁机制。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1 介绍

  • 说明:保证一个类仅有一个实例,并提供一个访问它的全局访问点。(整个系统只需要拥有一个全局对象时,例如日志,数据库连接)

  • 作用:主要解决一个全局使用的类频繁地创建与销毁。

  • 注意:在使用单例模式时,构造函数是私有的。

  • 优点:
    1、在内存里只有一个实例,减少了内存的开销,尤其时频繁的创建和销毁实例。
    2、避免对资源的多重占用(写文件操作)‘

2 实现方法

  • 懒汉模式
  • 饿汉模式

2.1 懒汉模式

  • 懒汉:
    它在需要对象时,才判断是否已有对象,如果没有就立即创建一个对象,然后返回;如果已经有对象了,就不创建立即返回。
    只在外部对象第一次请求实例的时候才去创建。(调用时才实例化)
  • 特点:运行时获得对象的速度慢,但加载类的时候比较快。在整个应用的生命周期只有一部分时间在占用资源。
  • 使用:
    1)线程不安全写法:
static Log GetInstance(
### Qt中实现单例模式的方法 在Qt框架中,单例模式可以通过多种方式实现。以下是几种常见的实现方法及其特点: #### 方法一:使用 `Q_GLOBAL_STATIC` 宏 `Q_GLOBAL_STATIC` 是 Qt 提供的一个便捷宏,用于创建全局静态对象并支持延迟初始化[^1]。这种方式简单高效,适用于需要复杂构造参数的情况。 ```cpp #include <QObject> #include <QGlobalStatic> class MySingleton : public QObject { Q_OBJECT private: explicit MySingleton(QObject *parent = nullptr) : QObject(parent) {} public: static MySingleton *getInstance() { static QGlobalStatic<MySingleton> instance; return instance(); } }; // 使用示例 MySingleton *singleton = MySingleton::getInstance(); ``` 这种方法的优点在于无需手动管理内存释放,因为 `QGlobalStatic` 会在程序退出时自动清理资源[^1]。 --- #### 方法二:懒汉模式(线程安全) 懒汉模式是指在第一次调用时才创建实例。为了确保线程安全性,可以结合 `QMutex` 进行同步控制[^5]。 ```cpp #include <QObject> #include <QMutex> class Singleton : public QObject { Q_OBJECT private: Singleton(QObject *parent = nullptr) : QObject(parent) {} public: static Singleton *getInstance(); private: static Singleton *m_instance; static QMutex m_mutex; }; Singleton *Singleton::m_instance = nullptr; Singleton *Singleton::getInstance() { if (m_instance == nullptr) { // 第一次检测 QMutexLocker locker(&m_mutex); // 锁定互斥量 if (!m_instance) { // 第二次检测 m_instance = new Singleton; } } return m_instance; } // 初始化静态成员变量 QMutex Singleton::m_mutex; Singleton *Singleton::m_instance = nullptr; // 使用示例 Singleton *singleton = Singleton::getInstance(); ``` 这种实现方式适合多线程环境下的单例模式需求,能够有效防止多个线程同时创建实例[^5]。 --- #### 方法三:饿汉模式 饿汉模式在类加载时就立即创建实例,因此存在线程安全问题。但由于实例始终存在,可能会浪费一定的内存资源[^4]。 ```cpp #include <QObject> class Singleton : public QObject { Q_OBJECT private: Singleton(QObject *parent = nullptr) : QObject(parent) {} public: static Singleton *getInstance() { return &m_instance; } private: static Singleton m_instance; }; Singleton Singleton::m_instance; // 使用示例 Singleton *singleton = Singleton::getInstance(); ``` 饿汉模式的特点是以空间换取时间,适合那些需要频繁使用的单例对象。 --- #### 方法四:智能指针实现 利用 C++ 的智能指针(如 `std::unique_ptr` 或 `QScopedPointer`),可以在保证线程安全的同时简化资源管理逻辑[^4]。 ```cpp #include <QObject> #include <QScopedPointer> #include <QMutex> class Singleton : public QObject { Q_OBJECT private: Singleton(QObject *parent = nullptr) : QObject(parent) {} public: static Singleton *getInstance(); private: static QScopedPointer<Singleton> m_instance; static QMutex m_mutex; }; Singleton *Singleton::getInstance() { if (!m_instance) { QMutexLocker locker(&m_mutex); if (!m_instance) { m_instance.reset(new Singleton); } } return m_instance.data(); } // 初始化静态成员变量 QScopedPointer<Singleton> Singleton::m_instance; QMutex Singleton::m_mutex; // 使用示例 Singleton *singleton = Singleton::getInstance(); ``` 这种方法仅实现了线程安全,还通过智能指针自动管理了对象生命周期[^4]。 --- #### 方法五:基于宏的通用实现 如果希望减少重复代码,可以定义一个通用的单例模板宏。 ```cpp #define DECLARE_SINGLETON(Class) \ private: \ Class(); \ friend struct GlobalInitializer_##Class; \ public: \ static Class *getInstance(); \ private: \ static Class *s_instance; \ static QMutex s_mutex; #define IMPLEMENT_SINGLETON(Class) \ Class *Class::s_instance = nullptr; \ QMutex Class::s_mutex; \ Class *Class::getInstance() { \ if (!s_instance) { \ QMutexLocker locker(&s_mutex); \ if (!s_instance) { \ s_instance = new Class; \ } \ } \ return s_instance; \ } // 示例类 class MyClass : public QObject { Q_OBJECT DECLARE_SINGLETON(MyClass) }; IMPLEMENT_SINGLETON(MyClass) // 使用示例 MyClass *myClass = MyClass::getInstance(); ``` 这种宏的方式提高了代码复用性和可维护性[^4]。 --- ### 总结 以上介绍了几种在 Qt 中实现单例模式的方法,每种方法都有其适用场景: - 如果追求简洁且涉及复杂构造,则推荐使用 `Q_GLOBAL_STATIC`。 - 对于多线程环境,建议采用带 `QMutex` 的懒汉模式或智能指针实现。 - 饿汉模式则更适合性能敏感的应用场合。 无论选择哪种方式,都需要注意以下几点: 1. 确保实例的唯一性; 2. 考虑线程安全问题; 3. 合理管理对象生命周期。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值