首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >QObject实例池

QObject实例池
EN

Stack Overflow用户
提问于 2014-07-02 03:53:32
回答 2查看 1.3K关注 0票数 4

我有个问题我不知道怎么解决..。

我们有通用对象池。当请求对象时,池将返回QSharedPointer到第一个可用实例,并指定了自定义Deleter。当QSharedPointer实例引用计数为0时,删除器只将对象返回到池。对于普通的对象来说,一切都很好。当在Qt 5中编译时,它对QObject后继者也很好。

但是,如果在QT4.6中编译-问题就开始了:当第二次请求同一个对象时-应用程序退出时会出现错误:

"QSharedPointer:指针xxx已经有引用计数“

我写了一个简单的测试:

代码语言:javascript
复制
QObject* obj = new QObject();
QSharedPointer<QObject> p(obj, deleter); // deleter here does nothing
p.clear();
QSharedPointer<QObject> p2(obj, deleter); // this crashes the app

当在QT4.6中编译时,这肯定会失败。同样:在QT5.x中可以很好地工作。

查看Qt源代码,它发现,当使用这个QObject作为QSharedPointer参数时,4.6会在QSharedPointer中初始化内部参考计数器。这样做是为了确保没有两个智能指针可以指向同一个对象,并且它只能在析构函数中被重置。

当Qt5实例被包装到智能指针中时,QObject不检查ref计数器值,因此它可以工作。

有人知道更旧的Qt版本的解决方法吗?是否有任何方法可以完全重置内部Qt状态,包括ref计数器?任何暗示都是非常欢迎的。

EN

回答 2

Stack Overflow用户

发布于 2014-08-11 18:08:15

假设您有池以避免内存分配和去分配,您应该只分配一次内存,然后在请求并返回“新”对象时显式调用构造函数和析构函数。

代码语言:javascript
复制
/* deleter calls destructor explicitly when return object to pool */
void deleter(QObject *object) {
    object->~QObject();
    mark_as_available();
}

/* allocate (one object) pool memory without calling constructor*/
QObject *object = ::operator new(sizeof(QObject));

/* request object - calling constructor on already allocated memory */
mark_as_taken();
return QSharedPointer(::new (object) QObject, &deleter);

/* deallocate pool memory without calling destructor */
::operator delete(object);
票数 0
EN

Stack Overflow用户

发布于 2018-11-04 12:50:44

只允许一次从QSharedPointer创建QObject,后者则需要复制现有的QSharedPointer实例。

根据Qt 4 和5文档:

当指针超出作用域时,QSharedPointer 将删除它所持有的指针,条件是没有其他QSharedPointer对象引用它。

因此,您的样本行为如下:

代码语言:javascript
复制
QObject* obj = new QObject();
QSharedPointer<QObject> p(obj, deleter); // deleter here does attach to "obj"
p.clear(); //this does cause delete of "obj"
QSharedPointer<QObject> p2(obj, deleter); // using deleted pointer will cause crash (if you are lucky XD)

使用QWeakPointer不会删除QObject和断言:

"QSharedPointer:指针xxx已经有引用计数“

是为了确保您不会意外地创建多个删除器(这确实安全了我的一天,我使用的是QSharedPointer,意思是QWeakPointer),但它有时会妨碍您。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/24522600

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档