我已经约了Qt单证阅读QPointer
,QSharedPointer
和QWeakPointer
类.它说:
QPointer
是一个模板类,它提供了对Qt对象的保护指针,其行为类似于普通的C++指针,只是当被引用的对象被销毁并且没有产生"悬空指针"时它会自动设置为0.
QSharedPointer
class拥有对共享指针的强引用.
QWeakPointer
class持有对共享指针的弱引用.
我的问题是"这些课程有什么区别?".即指向对象的指针和指针的引用之间的区别是什么?它们都是指向具有不同机制和行为的对象的指针吗?
我们的应用程序的设计非常差-它既使用std::shared_ptr
和QObject
亲子关系来管理我们的一些对象。当QObject::~QObject
删除其子对象,然后shared_ptr
尝试也将其删除时,这会导致段错误。
我们讨论了此问题,但目前尚无轻松解决此问题的方法,因此在我们对其进行修复之前,我将需要使用一些肮脏的技巧。
现在我有一个std::shared_ptr<MyObject> getMyObjectPtr()
功能。我需要将结果放入QPointer<MyObject>
-QPointers是弱指针,仅指示他们管理的QObject是否已删除。我无法以任何方式更改该功能,它将破坏整个应用程序。
我使用自定义脱发器尝试了一些技巧,但这似乎行不通。
// 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());
Run Code Online (Sandbox Code Playgroud)
但是,以这种方式,一旦函数结束,指针将被删除。大概,自定义脱机器与数据一起移动。
我找到了QPointer.还有其他人吗?
根据SGI关于关联容器的文档,"由于元素是根据其键存储的,因此与每个元素相关联的键必须是不可变的".我有时使用指针作为std :: map的键,因为虽然指向的对象可能是可变的,但指针本身是常量.
QPointer在技术上是一个模仿指针的对象,Qt的doc说我们可以像指针一样使用QPointers.由于QPointer对象本身可能在执行期间发生变化,它仍然可以用作std :: map容器的键吗?
编辑1:我不能使用QMap,我必须坚持使用std :: map.
编辑2:当我使用QPointer时代码编译.问题是我是否应该在运行时期待令人不快的意外.
QPointer
有一个方法,clear()
。
清除这个 QPointer 对象。
我不确定“清楚”究竟是什么意思。在我看来,这可能意味着
或者
QPointer<T>
对象不再绑定到任何指针。或许还有别的意思?你能告诉我它实际上是做什么的吗?
根据http://doc.qt.io/qt-5/qpointer.html,QPointer非常有用.但我发现在以下情况下它可能效率低下:
如果我想要显示标签三次或做其他事情,我必须使用
if(label) label->show1();
if(label) label->show2();
if(label) label->show3();
代替
if(label) { label->show1();label->show2();label->show3(); }
只是因为标签可能在或之后在另一个线程中被销毁label->show1();
label->show2();.
除了三个ifs之外还有一种漂亮的方式来获得相同的功能吗?
另一个问题是,在if(标签)之后销毁标签时,if(label) label->show1();
仍然是错误的吗?
我没有多线程程序的经验.任何帮助表示赞赏.;)
我的宠物项目已经到了我应该开始跟踪指针寿命的地步,我正在尝试为其开发一些系统。遗憾的是,流行的到处使用智能指针的建议并不适用,因为 Qt API 本身在任何情况下都使用裸指针。所以,我想到的是:
对于 Qt 拥有的一切,
QPointer
,在转换为裸之前进行isNull()
检查。对于我完全拥有的所有东西,请按照建议使用智能指针。我将使用std::
这里的版本。
令我烦恼的案子。对于切换所有权的对象(例如从布局中添加/删除的小部件)
delete
在适当的时候手动进行。建议、意见、建议?我自己不太喜欢这个方案。
boost::bind
处理boost::shared_ptr
与原始指针相同的方式.
QObject * object(new QObject);
boost::shared_ptr<QObject> sharedObject(new QObject);
bind(&QObject::setObjectName, object, _1)( "name" );
bind(&QObject::setObjectName, sharedObject, _1)( "name" );
Run Code Online (Sandbox Code Playgroud)
我希望有一个boost::bind
处理QPointers
作为原始指针指针.
QPointer<QObject> guardedObject(new QObject);
// i want to write it like this
bind(&QObject::setObjectName, guardedObject, _1)( "name" );
//now i have to do it like this
bind(&QObject::setObjectName, bind(&QPointer<QObject>::data, guardedObject), _1)( "name" );
Run Code Online (Sandbox Code Playgroud)
是否有人为此专业化QPointer
?
如果不是,你知道从哪里开始或需要专门做什么,所以我可以自己做.
对于这个奇怪的标题感到抱歉,如果你能想到一个,请随时提出更好的标题.
这是我的问题.
我有一个看起来像这样的结构:
QObject - > MyBase - > MyDerived
然后我有一个函数将任何派生类型作为QPointer;
void function(QPointer<MyBase> base) {
...
}
Run Code Online (Sandbox Code Playgroud)
问题是现在我无法QPointer<MyDerived>
进入这个函数,如果我使用标准指针,我会这样做.我是否必须转换此对象以使其适合该功能?或者我应该只使用普通指针?
此外,当您分配失败的对象时,是否有人知道标准行为?你是否应该总是在try-block中执行此操作或将其包装在某个内容中以检查它是否为null?我阅读了Qt文档,他们说如果分配失败,他们的大多数类都会返回一个空值.该语句何时为true,如果我不想使用try-catch,我该怎么办?
qpointer ×9
c++ ×8
qt ×7
pointers ×5
boost-bind ×1
c++11 ×1
heap-memory ×1
shared-ptr ×1
stl ×1