c++ - Qt 基类函数定义
问题描述
我正在使用 gcc 4.8.5 在使用 Qt5 的项目中构建模板库,目标是发送和接收不共享继承层次结构的类型。我想出的一种可能的解决方案是,基类可以简单地定义信号和插槽,而派生类可以提供实现,这很有效。现在,为了编译时优化和运行时性能,如果我在基类中有数百个这样的方法会发生什么?
我无法找到的另一个有效问题似乎是当两个派生类继承同一个对象时在编译期间会发生什么。以下面的例子为例:
class A{}
class B : A{}
class C : A{}
这种结构有编译时的好处吗?此外,Qt 不会为一个类创建 moc,除非它定义了一个信号或插槽,所以会有
class A {
void slot_1();
//...
void slot_100();
}
停止编译,这是否有任何运行时开销?我知道 Qt 插槽下面只是一个函数,因此在内存中只创建了一个函数。此外,我知道派生类必须链接 moc_a.o 文件,但我不太确定链接器能够优化到什么程度。
注意:我知道这违反了 SRP 和 OCP,但上面列出了我最大的担忧和障碍。只要它们不是不必要的复杂且编译时友好,我愿意研究替代示例和解决方法。ISP 也出局了,我根本没有做那么多的多重继承。
解决方案
这是一个 XY 问题:您正在询问解决方案,但您要解决的实际问题是什么?这些类代表什么?“发送和接收类型”是什么意思?至于不共享继承层次结构,有一些简单的方法:一个通用接口可以由一个通用实现的方法提供,如果你添加Q_GADGET
或Q_OBJECT
到类中,你可以自省该方法——假设它们已经不是QObject
s。如果你使用QObject
,那么你可以通过编程方式调用方法QMetaObject::invokeMethod
,或者通过QMetaMethod::invokeOnGadget
on类型,并且除了自身Q_GADGET
之外确实不需要任何通用接口。QObject
例子:
#include <QtCore>
class Class1 {
Q_GADGET
public:
Q_INVOKABLE void foo() { qDebug() << "Class1::foo"; }
};
class Class2 : public QObject {
Q_OBJECT
public:
Q_SLOT void foo() { qDebug() << "Class2::foo"; }
};
class Class3 : public QObject {
Q_OBJECT
public:
Q_SLOT void bar() { qDebug() << "Class3::bar"; }
};
template <class C> QMetaMethod getMethod(const C& c, const char *signature) {
auto const &mo = c.staticMetaObject;
auto const nSignature = QMetaObject::normalizedSignature(signature);
int index = mo.indexOfMethod(nSignature);
if (index >= 0)
return mo.method(index);
return {};
}
int main() {
Class1 c1;
Class2 c2;
Class3 c3;
auto foo1 = getMethod(c1, "foo()");
auto foo2 = getMethod(c2, "foo()");
auto bar3 = getMethod(c3, "bar()");
foo1.invokeOnGadget(&c1);
foo2.invoke(&c2);
bar3.invoke(&c3);
}
#include "main.moc"
推荐阅读
- node.js - 无法在本地运行 Next JS 开发服务器
- java - 如何使用java从firebase数据库中的列表中获取所有值?
- c# - 在“eventViewer = null”中覆盖eventViewer会泄漏“eventViewer在C#中引用的资源”
- wordpress - 为什么我的联系表 7 字段验证也禁止空条目?
- python - 无法使用 Selenium webdriver Python 选择元素(类)
- python - 使用函数分配列表中的项目以获取所需的地址
- java - Spring Native Unresolved 类
- flutter - StreamBuilder 给我错误 Cannot read properties of undefined (reading 'app') CRUD APP FLUTTER
- python - 如何使用 MAPS API 查找城市中的所有社区
- jmeter - JMeter 插件管理器无法下载插件存储库