首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Qt: typeid替代方案

Qt: typeid替代方案
EN

Stack Overflow用户
提问于 2013-12-19 14:50:08
回答 3查看 4.5K关注 0票数 6

我想知道Qt是否提供了一种替代typeid来识别变量类型并以人类可读的格式获取它们的名称。我的具体问题如下:

代码语言:javascript
复制
struct gArgument{
    QString type; 
    void* arg;
};

void gargConverter(gArgument* oArg, T data){
    oArg->type = typeid(data).name();
    oArg->arg = static_cast<void*> (&data);
}

其思想是将变量泛化为函数的输入。作为一个边节点,tyeinfo似乎无法在我的系统上正常工作(我在Windows 7上使用MinGW ),如果我尝试:

代码语言:javascript
复制
  int i; std::cout <<   typeid(i).name() << std::endl;
  QString s; std::cout <<   typeid(s).name() << std::endl;
  double d; std::cout <<   typeid(d).name() << std::endl;
  float f; std::cout <<   typeid(f).name() << std::endl;

我得到了

代码语言:javascript
复制
i
7QString
d
f

有什么建议吗?

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2013-12-19 14:54:48

你可以用

const char * QVariant::typeName () const 返回存储在变体中的类型的名称。返回的字符串描述用于存储数据的C++数据类型:例如,"QFont“、"QString”或"QVariantList“。无效变量返回0。

这将适用于POD和注册的内置Qt类型。不过,您需要使用跟随法注册您的自定义类型。

int qRegisterMetaType(const char * typeName)

您可以尝试的另一件事(虽然对QVariant来说有些多余)是以以下方式处理对象的QMetaObject:

const char * QMetaObject::className() const 返回类名。

const QMetaObject * QObject::metaObject() const [virtual] 返回指向此对象的元对象的指针。 元对象包含继承QObject的类的信息,例如类名、超类名称、属性、信号和插槽。每个包含QObject宏的Q_OBJECT子类都有一个元对象. 信号/时隙连接机制和属性系统都需要元对象信息。函数还使用元对象。 如果没有指向实际对象实例的指针,但仍然希望访问类的元对象,则可以使用staticMetaObject。

不用说,这只适用于QObjects,而不适用于QString等等。您需要创建QObject子类。

您也可以使用一些QMetaType来创建,但是有点不同,所以我在这里只想说明一下:

int QMetaType::type(const char * typeName) [static] 返回名为typeName的类型的句柄,如果没有这种类型,则返回QMetaType::不明类型。

在这里,您可以找到所有类型:

http://qt-project.org/doc/qt-5.1/qtcore/qmetatype.html#Type-enum

票数 5
EN

Stack Overflow用户

发布于 2013-12-19 20:05:12

你的名字都乱七八糟了。这是非常好的,因为行为是实现定义的。要使它具有人类可读性,您需要对名称进行篡改的编译器上的名称进行分解(gcc和llvm)。

下面的代码可以在g++、llvm++和MS Visual C++下工作,因此它可以尽可能地移植。

代码语言:javascript
复制
#include <iostream>
#ifndef _MSC_VER
#include <cxxabi.h>
#endif

struct QEvent { virtual ~QEvent() {} };

struct MyEvent : public QEvent {};

#ifndef _MSC_VER
template <typename T> void dumpType(T val)
{
  int status;
  char * realname = abi::__cxa_demangle(typeid(val).name(), 0, 0, &status);
  std::cout << realname << std::endl;
  free(realname); //important!
}

template <typename T> void dumpType(T *ptr)
{
  int status;
  char * realname = abi::__cxa_demangle(typeid(*ptr).name(), 0, 0, &status);
  std::cout << realname << std::endl;
  free(realname); //important!
}
#else
template <typename T> void dumpType(T val)
{
  std::cout << typeid(val).name() << std::endl;
}
template <typename T> void dumpType(T *ptr)
{
  std::cout << typeid(*ptr).name() << std::endl;
}
#endif

int main() {
  QEvent * base = new QEvent;
  QEvent * der = new MyEvent;
  dumpType(int());
  dumpType(base);
  dumpType(der);
}

gcc和LLVM的产出:

代码语言:javascript
复制
int
QEvent
MyEvent

MSVC的输出:

代码语言:javascript
复制
int
class QEvent
class MyEvent
票数 1
EN

Stack Overflow用户

发布于 2013-12-19 15:03:54

看起来,您正在尝试获得通用变量,类似于QVariantQVariant完美地适用于所有基本类型和所有Qt类型。其他类型可以是已注册到qt元数据系统。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/20684712

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档