zoukankan      html  css  js  c++  java
  • Qt中QScopedPointer的用法,实操验证。

    还是老规矩,QScopedPointer概念性的东西我就不赘述了,网上百度一抓一大把。

    这里主要用实际的例子来说明一下QScopedPointer这个智能指针中data()和take()的用法,这里面是有坑的。

    我们先来说一下data()和take()分别表示的是什么意思?

    首先你可以把QScopedPointer看成是一个容器。

    take()接口的意思是从这个容器中将对象删除,并返回之前放在这个容器中的对象或者数据,QScopedPointer不再拥有这个对象的指针。

    data()接口的意思就是返回容器中的指针,QScopedPointer还是拥有这个对象的指针的。

    这个take()感觉用起来有点像qt中队列(queue)的取操作(dequeue)。

    有一种情况我们需要考虑的,就是在函数中使用了QScopedPointer如果来避免野指针的情况,本篇文章主要就是解决这个问题。

    实际的例子是这样的,我先在.h中定义了一个单例模式的接口。

    static ScreenWidget *Instance();

    然后在.cpp文件中实现这个接口

    QScopedPointer<ScreenWidget> ScreenWidget::self;
    ScreenWidget *ScreenWidget::Instance()
    {
        if (self.isNull()) 
        {
            static QMutex mutex;
    
            QMutexLocker locker(&mutex);
    
            if (self.isNull()) 
            {
                self.reset(new ScreenWidget);
            }
        }
    
        return self.data();
    }

    这里用的是data()。

    在main.cpp文件中是如下使用方式。

        ScreenWidget* p1 = ScreenWidget::Instance();
        p1->showFullScreen();

    这种情况程序会挂掉。

     这里就是出现了野指针的问题,因为在函数中使用data(),在函数结束以后QScopedPointer会被释放,QScopedPointer内的对象也会被释放,那么p1就是一个野指针了。程序自然就崩溃了。

    ScreenWidget::Instance()->showFullScreen();

    如果程序改成以上的样子程序就没什么问题。不存在野指针的情况。

    QScopedPointer<ScreenWidget> ScreenWidget::self;
    ScreenWidget *ScreenWidget::Instance()
    {
        if (self.isNull()) 
        {
            static QMutex mutex;
    
            QMutexLocker locker(&mutex);
    
            if (self.isNull()) 
            {
                self.reset(new ScreenWidget);
            }
        }
    
        return self.take();
    }

    如果将上一段代码的返回值改成take()。

    ScreenWidget* p1 = ScreenWidget::Instance();
    p1->showFullScreen();

    再次使用这种方式,程序没有问题,因为take()接口在返回的时候QScopedPointer删除了对象,但是也保留了对象的指针。p1就不会出现野指针的情况。

    ScreenWidget::Instance()->showFullScreen();

    如果换成这样的形式,程序也没有崩溃,因为没有指针指向的情况没有野指针存在。

  • 相关阅读:
    Cocos Creator 图集 (TexturePacker、自动图集功能 、压缩纹理)
    Cocos Creator 下载不同版本引擎
    Cocos Creator 源码 (位置,阅读、修改)
    Laya3D Unity商店免费下载3D资源使用(Unity插件支持哪些导出)
    三 Laya3D 加载资源 (场景/预设/模型网格/材质/动画文件/贴图/粒子)
    二 Laya3D github demo下载并使用
    一 Laya3D Unity下载和插件安装
    AndroidUI设计之布局-详细解析布局实现
    Android 监听ScrollView的滑动
    【Android进阶】Android程序与JavaScript之间的简单调用
  • 原文地址:https://www.cnblogs.com/joorey/p/14850467.html
Copyright © 2011-2022 走看看