首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >将std::shared_ptr转换为QPointer

将std::shared_ptr转换为QPointer
EN

Stack Overflow用户
提问于 2017-07-03 12:03:18
回答 1查看 904关注 0票数 5

我们的应用程序设计非常糟糕--它同时使用std::shared_ptrQObject父子关系来管理我们的一些对象。当QObject::~QObject删除它的子对象,然后shared_ptr也尝试删除它时,这会导致分段错误。

我们讨论了这个问题,但是目前还没有办法很容易地解决这个问题,所以在我们修复之前,我需要使用很少的脏黑客。

现在我有一个std::shared_ptr<MyObject> getMyObjectPtr()函数。我需要将结果放入QPointer<MyObject>中-- QPointers是弱指针,仅指示它们管理的QObject是否被删除。我不能以任何方式改变这个函数,它会破坏整个应用程序。

我尝试了很少与自定义经销商,但这似乎不起作用。

代码语言:javascript
复制
// get the shared_ptr from inacessible API
std::shared_ptr<MyObject> oldPtr(getMyObjectPtr());
// create a new pointer that never deletes it's value
std::shared_ptr<MyObject> newPtr(nullptr, [](MyObject*) {});
// Move pointer from old to new non-deleting ptr
newPtr.swap(oldPtr);
QPointer<MyObject> qptr(newPtr.get());

但是,这样,一旦我的函数结束,指针就会被删除。据推测,自定义释放器与数据一起移动。

EN

回答 1

Stack Overflow用户

发布于 2017-07-03 14:41:52

我认为这个问题没有任何好的解决方案,只是开始重构代码,以便通过QObject风格的父/子关系或shared_ptr<>引用计数来管理任何给定的对象--但绝不是同时存在于同一个对象中。这两种方法太不一样了,很难调和。

尽管如此,为了在不进行太多重新设计的情况下完成上述工作,您可能可以做的一件事是:与其让shared_ptr<>指向您的QObject,不如让shared_ptr指向(非基于QObject的)QObject的一个由shared_ptr管理的子对象。

也就是说,而不是这样:

代码语言:javascript
复制
class MyQObject : public QObject 
{
public:
   MyQObject(int x, int y, int z, QObject * parent)
      : QObject(parent), m_x, m_y, m_z {/* empty */}

   int getX() const {return m_x;}
   int getY() const {return m_y;}
   int getZ() const {return m_z;}

private:
   int m_x, m_y, m_z;
};

[...]

QObject * parent = new QObject;
shared_ptr<MyQObject> ptr(new MyQObject(1,2,3,parent));   // d'oh!  trouble!

做这样的事:

代码语言:javascript
复制
class MyData
{
public:
   MyData(int x, int y, int z) : m_x(x), m_y(y), m_z(z)

   int getX() const {return m_x;}
   int getY() const {return m_y;}
   int getZ() const {return m_z;}

private:
   int m_x, m_y, m_z;
};

class MyQObject : public QObject
{
public:
   MyQObject(int x, int y, int z, QObject * parent)
      : QObject(parent), m_data(make_shared<MyData>(x,y,z)) {/* empty */}

   int getX() const {return m_data->getX();}
   int getY() const {return m_data->getY();}
   int getZ() const {return m_data->getZ();}

   shared_ptr<MyData> getData() {return m_data;}

private:
   shared_ptr<MyData> m_data;
};

[...]

QObject * parent = new QObject;
QObject * myObj = new MyQObject(1,2,3,parent));
shared_ptr<MyData> ptr(myObj->getData());   // no problem!

这样,Qt样式的代码可以访问QObject和MyData,而shared_ptr风格的代码可以访问MyData。(当然,如果您的shared_ptr风格的代码也需要访问QObject本身,那么您可能就不走运了,因为Qt将决定何时何地删除QObject,并且不尊重shared_ptr语义)

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

https://stackoverflow.com/questions/44885112

复制
相关文章

相似问题

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