qt基础之全局静态变量

文章介绍了Qt中的Q_GLOBAL_STATIC宏,用于定义带有参数的全局静态变量,以及QThreadPool如何使用这类全局静态变量。它详细阐述了内联函数和原子操作确保全局变量的初始化和生命周期管理。
摘要由CSDN通过智能技术生成

Q_GLOBAL_STATIC

用于定义全局静态变量

#define Q_GLOBAL_STATIC(TYPE, NAME)                                         \
    Q_GLOBAL_STATIC_WITH_ARGS(TYPE, NAME, ())

Q_GLOBAL_STATIC_WITH_ARGS

带有参数的全局静态变量宏
在匿名命名空间内定义了命名空间Q_QGS_ ## NAME,该命名空间内定义了

  • 类型:typedef TYPE Type
  • 原子操作变量:QBasicAtomicInt guard
  • 内联函数:Type *innerFunction()
    通过类模板QGlobalStatic来定义全局静态变量
#define Q_GLOBAL_STATIC_WITH_ARGS(TYPE, NAME, ARGS)                         \
    namespace { namespace Q_QGS_ ## NAME {                                  \
        typedef TYPE Type;                                                  \
        QBasicAtomicInt guard = Q_BASIC_ATOMIC_INITIALIZER(QtGlobalStatic::Uninitialized); \
        Q_GLOBAL_STATIC_INTERNAL(ARGS)                                      \
    } }                                                                     \
    static QGlobalStatic<TYPE,                                              \
                         Q_QGS_ ## NAME::innerFunction,                     \
                         Q_QGS_ ## NAME::guard> NAME;

内联函数innerFunction

是通过Q_GLOBAL_STATIC_INTERNAL来定义的
采用双重检查方式来初始化全局静态变量。
原子变量状态值使用枚举

enum GuardValues {
    Destroyed = -2,
    Initialized = -1,
    Uninitialized = 0,
    Initializing = 1
};

开始原子变量值为Uninitialized,构造完后状态为Initialized,析构时状态为Destroyed

#define Q_GLOBAL_STATIC_INTERNAL(ARGS)                                  \
    Q_DECL_HIDDEN inline Type *innerFunction()                          \
    {                                                                   \
        static Type *d;                                                 \
        static QBasicMutex mutex;                                       \
        int x = guard.loadAcquire();                                    \
        if (Q_UNLIKELY(x >= QtGlobalStatic::Uninitialized)) {           \
            QMutexLocker locker(&mutex);                                \
            if (guard.load() == QtGlobalStatic::Uninitialized) {        \
                d = new Type ARGS;                                      \
                static struct Cleanup {                                 \
                    ~Cleanup() {                                        \
                        delete d;                                       \
                        guard.store(QtGlobalStatic::Destroyed);         \
                    }                                                   \
                } cleanup;                                              \
                guard.storeRelease(QtGlobalStatic::Initialized);        \
            }                                                           \
        }                                                               \
        return d;                                                       \
    }

类模板QGlobalStatic

调用innerFunction创建全局静态变量
操作符(),->或者Type *调用innerFunction函数得到全局变量指针,如果全局变量已经销毁,则返回0
操作符*返回全局静态变量的引用

template <typename T, T *(&innerFunction)(), QBasicAtomicInt &guard>
struct QGlobalStatic
{
    typedef T Type;

    bool isDestroyed() const { return guard.load() <= QtGlobalStatic::Destroyed; }
    bool exists() const { return guard.load() == QtGlobalStatic::Initialized; }
    operator Type *() { if (isDestroyed()) return 0; return innerFunction(); }
    Type *operator()() { if (isDestroyed()) return 0; return innerFunction(); }
    Type *operator->()
    {
      Q_ASSERT_X(!isDestroyed(), "Q_GLOBAL_STATIC", "The global static was used after being destroyed");
      return innerFunction();
    }
    Type &operator*()
    {
      Q_ASSERT_X(!isDestroyed(), "Q_GLOBAL_STATIC", "The global static was used after being destroyed");
      return *innerFunction();
    }
};

应用

qt中的线程池中使用到

Q_GLOBAL_STATIC(QThreadPool, theInstance)
class Q_CORE_EXPORT QThreadPool : public QObject
{
	.........
public:
   	..........
    static QThreadPool *globalInstance();
    ......
};
QThreadPool *QThreadPool::globalInstance()
{
    return theInstance();
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

kgduu

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值