Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/qt/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 对基本非QObject类的虚函数进行slotify是否可以_C++_Qt - Fatal编程技术网

C++ 对基本非QObject类的虚函数进行slotify是否可以

C++ 对基本非QObject类的虚函数进行slotify是否可以,c++,qt,C++,Qt,如果我在基本的非QObject类中声明一个函数virtual,然后将其覆盖为派生类中的一个插槽,该派生类具有Q_OBJECT宏,并且QObject作为基类之一,那么它应该工作正常吗 是否可以保证虚拟呼叫正常工作?如果连接到派生类的插槽,会发生什么情况 class Base { public: virtual void f(); }; class Derived: public QObject, public Base { Q_OBJECT public slots: v

如果我在基本的非QObject类中声明一个函数virtual,然后将其覆盖为派生类中的一个插槽,该派生类具有Q_OBJECT宏,并且QObject作为基类之一,那么它应该工作正常吗

是否可以保证虚拟呼叫正常工作?如果连接到派生类的插槽,会发生什么情况

class Base
{
public:
    virtual void f();
};

class Derived: public QObject, public Base
{
    Q_OBJECT
public slots:
    virtual void f();
};
是的:

因为槽是普通成员函数,它们遵循普通C++。 直接调用时的规则。您还可以将插槽定义为虚拟插槽,这一点我们已经发现 在实践中很有用

在您的示例中,
Derived::f
是一个普通的虚函数。如果直接调用它,它将按预期工作,正如文档所述。当通过信号调用时,它由
qt\u static\u metacall
调用,该调用在
moc\u Derived.cpp
中生成,如下所示:

void Derived::qt_static_metacall(QObject *_o, QMetaObject::Call _c, 
                                 int _id,     void **_a)
{
    if (_c == QMetaObject::InvokeMetaMethod) {
        Q_ASSERT(staticMetaObject.cast(_o));
        Derived *_t = static_cast<Derived *>(_o);
        switch (_id) {
        case 0: _t->f(); break;
        default: ;
        }
    }
    Q_UNUSED(_a);
}
void派生::qt_static_metacall(QObject*_o,QMetaObject::调用_c,
内部id,无效**a)
{
if(_c==QMetaObject::InvokeMetMethod){
Q_ASSERT(staticMetaObject.cast(_o));
派生*_t=静态_转换(_o);
开关(_id){
案例0:_t->f();中断;
违约:;
}
}
Q_未使用(_a);
}
因此,它以正常的函数调用
\u t->f()
结束


请注意,无法通过信号调用
Base::f
。仅当当前对象实际上是
Base
实例而不是
派生的
实例时,才能执行此函数。由于
Base
不是基于QObject的,因此不能将其实例传递给
connect
函数。

这并不能真正解决问题。@LucTouraille你认为这是为什么?我认为它清楚地表明插槽的行为与正常功能一样(
virtual
或不)。最后,插槽调用会导致函数调用,因此应该正确处理虚拟性。@JohannesS:据我所知,问题不在于框架明确允许的虚拟插槽(如Riateche所述),但是关于将现有成员函数从基类转换为派生类中的插槽(还有一个潜在的问题,即基类甚至不是QObject)。@LucTouraille很抱歉,但我无法从这个问题中得到这种解释。如果你的解释是正确的,我请OP编辑这个问题以使其清晰。@JohannesS。Luc Touraille的解释是正确的,我不认为你的解释可以在我的问题中找到,无论如何,我将添加代码示例以更加清楚。显然,对你的问题似乎有一些不同的解释。你能澄清一下吗?比如说,添加一些示例代码?这与问题并不相关,但你应该知道这一点。@LucTouraille确实不相关。修正了。我在回答中提供了一些细节。