c++ - 使用 Qt 的元对象系统获取对象实例类名
问题描述
我有 3 节课:
class Being : public QObject {
Q_OBJECT
public:
explicit Being(QObject *parent = nullptr);
};
class Animal : public Being {
Q_OBJECT
public:
explicit Animal(QObject *parent = nullptr);
};
class Dog : public Animal {
Q_OBJECT
public:
explicit Dog(QObject *parent = nullptr);
};
存在的实现如下:
Being::Being(QObject *parent) : QObject(parent) {
qDebug() << staticMetaObject.className();
}
我有以下代码:
Being *pBeing = new Being();
Being *pAnimal = new Animal();
Being *pDog = new Dog();
问题是:有没有办法实现Being的构造函数,以便我可以访问指向我的Being基类的实际实例,以便上述代码的日志为:
Being
Animal
Dog
?
编辑:
我的意图是我希望能够拥有一个Animal.txt
,Being.txt
并将Doc.txt
在 Being 基类中处理。而且我需要知道,根据实例的类型,我是否需要 parseAnimal.txt
或Being.txt
获取Doc.txt
更多信息。
Qt 支持这个吗?有没有一种机制我可以使用 C++/Qt 来实现这一点?如果没有,是否有任何优雅的妥协解决方案?
解决方案
在构造函数中是不可能的,Being
因为尚未构造封闭对象,因此有关它的元数据不可用。但是,您可以编写在initialize
对象构造后应该调用的方法,例如使用 print 函数:
class Being : public QObject {
Q_OBJECT
public:
explicit Being(QObject *parent = nullptr) { qDebug() << this->metaObject()->className(); } // this will always print "Being"
void initialize() { qDebug() << this->metaObject()->className(); } // this will print the actual class name
};
class Animal : public Being {
Q_OBJECT
public:
explicit Animal(QObject *parent = nullptr) { initialize(); } // you can already use this method in the constructor
};
TEST(xxx, yyy)
{
Being* being = new Being();
Being* animal = new Animal();
being->initialize();
animal->initialize(); // or you can call it later
}
如果initialize
方法不是很好的解决方案,你总是可以通过Being
构造函数来破解它:explicit Being(QString name, QObject* parent = nullptr;
然后explicit Animal(QObject *parent = nullptr): Being("Animal") {}
,但我认为它不太优雅。
推荐阅读
- ios - 配置文件不包括 application-identifier 和 keychain-access-groups 权利
- multithreading - 不兼容的类型:“常规过程和方法指针”
- java - Java - 单词加扰器[保留第一个和最后一个字母]
- java - 如何扩展 ConnectionService?
- java - 获取多个 Element JSoup Java Android
- ios - 从 iOS 上的 React Native 应用程序访问 NSUserDefaults
- nrules - NRules 会议如何比较事实?
- amazon-web-services - AWS 访问密钥与密钥对
- ruby - 如何在两个字符/子字符串之间提取子字符串
- azure-data-factory-2 - Azure 数据工厂 V2 集 AzureRmDataFactoryV2Dataset:“表名”不能为空