我正在使用QT 5.7,由于我必须使用的库,我需要将一个QObject(的派生类)转换为void指针。
几个定义。我有一个只接受void指针的函数,我的类派生自QObject:
void oneFunction(void *obj);
class MyObj : public QObject
{
...
};
然后我创建并填充一个对象:
MyObj *ptr = new MyObj(parent);
ptr->.......
在某些时候我将它转换为void指针,因为我必须将它传递给函数。此演员表自动完成:
oneFunction(ptr);
然后,过了一段时间,我收到了我传递的指针,我需要将它转换回原来的类。该函数未修改指针:
void callbackFromOneFunction(void *theOldPointer)
{
MyObj *oldPtr = qobject_cast<MyObj*>(static_cast<QObject*>(theOldPointer));
if (oldPtr != nullptr)
{
... Now it's back, so use it
}
}
现在,整个程序是对的吗?你发现了一些问题/泄漏吗?有更好的解决方案吗?
谢谢
答案 0 :(得分:5)
我认为单static_cast
就足够了。
static_cast
不会在运行时检查类型,应该在确定类型正常时使用。在这种情况下,您确定,并且您不需要qobject_cast
。 qobject_cast
在运行时检查类型(类似于dynamic_cast
)。
static_cast
或C风格的演员阵容是可以的。虽然C风格的演员阵容在这里很好用,但不推荐使用,因为:
static_cast
是。static_cast
更具可读性,可以更轻松地进行搜索。当源类型为QObject *
或其派生时,单个qobject_cast
就足够了。
如果源类型是多态的,则使用dynamic_cast
。换句话说,dynamic_cast
仅用于 用于多态源类型(即具有至少一个虚函数的类)。在这样的类中,在编译时我们无法确定指向具有虚方法的基类的最派生类型的指针,只有在运行时我们才能确定它们。
关于动态投射void*
,允许投射但不投射。
在您的情况下void*
没有RTTI,因此qobject_cast
和dynamic_cast
都不能使用。
答案 1 :(得分:3)
如果 和只有,如果您确定指针不是,oneFunction(void*)
将永远不会触及指针Undefined,然后在你的程序的其他地方接受该指针的安全性,并将其输入回QObject
。请参阅this。
在这种情况下,这是完全有效的:
void callbackFromOneFunction(void *theOldPointer)
{
MyObj *oldPtr = qobject_cast<MyObj*>(static_cast<QObject*>(theOldPointer));
if (oldPtr != nullptr)
{
... Now it's back, so use it
}
}