在C ++ 11中检查对象类型 [英] Checking the object type in C++11

查看:132
本文介绍了在C ++ 11中检查对象类型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有B继承自A。

class A
{
};

class B : public A
{
};

我有三个对象。

A* a = new A();
A* a2 = new B();
B* b = new B();

我想要如果检查a是A类型的对象,a2是类型B的对象不是A),b是类型B的对象。

I'd like to if check a is object of type A, a2 is object of type B (not A), and b is object of type B.

我尝试了类型比较,但它不给我正确的答案。

I tried typed comparison, but it doesn't give me correct answer.

cout << (typeid(*a) == typeid(A)) << endl; // -> 1
cout << (typeid(*a2) == typeid(A)) << endl; // -> 1
cout << (typeid(*b) == typeid(A)) << endl; // -> 0

cout << (typeid(*a) == typeid(B)) << endl; // -> 0
cout << (typeid(*a2) == typeid(B)) << endl; // -> 0
cout << (typeid(*b) == typeid(B)) << endl; // -> 1

我尝试了动态转换,但我遇到了编译错误。

I tried dynamic casting, but I got compile error.

B* derived = dynamic_cast<B*>(a);
if (derived) {
    cout << "a is B";
}
derived = dynamic_cast<B*>(a2);
if (derived) {
    cout << "a2 is B";
}
derived = dynamic_cast<B*>(b);
if (derived) {
    cout << "b is B";
}

typename.cpp: In function 'int main(int, char**)':
typename.cpp:27:36: error: cannot dynamic_cast 'a' (of type 'class A*') to type 'class B*' (source type is not polymorphic)
     B* derived = dynamic_cast<B*>(a);
                                    ^
typename.cpp:31:34: error: cannot dynamic_cast 'a2' (of type 'class A*') to type 'class B*' (source type is not polymorphic)
     derived = dynamic_cast<B*>(a2);

我使用静态转换,但我得到的答案错了。

I used static casting, but I got the answer wrong.

B* derived = static_cast<B*>(a);
if (derived) {
    cout << "a is B"; // -> YES
}
derived = static_cast<B*>(a2);
if (derived) {
    cout << "a2 is B"; // -> YES
}
derived = dynamic_cast<B*>(b);
if (derived) {
    cout << "b is B"; // -> YES
}

如何正确识别 C ++ 11

推荐答案

一些类是多态的,一些是非多态的。一些是非多态的。

Some classes are polymorphic, some are non-polymorphic.

多态类有一个或多个虚函数类有零个虚函数。

A polymorphic class has one or more virtual functions (possibly inherited), a non-polymorphic class has zero virtual functions.

您的A和B是非多态的。

Your A and B are non-polymorphic.

A的多态版本B将显示您想要的行为:

A polymorphic version of A and B will exhibit the behaviour you want:

#include <iostream>
#include <typeinfo>

using namespace std;

struct A
{
    virtual ~A() {}; // add virtual function
};

class B : public A
{
};

A* a = new A();
A* a2 = new B();
B* b = new B();

int main()
{
    cout << (typeid(*a) == typeid(A)) << endl; // -> 1
    cout << (typeid(*a2) == typeid(A)) << endl; // -> 0 <-- CHANGED
    cout << (typeid(*b) == typeid(A)) << endl; // -> 0

    cout << (typeid(*a) == typeid(B)) << endl; // -> 0
    cout << (typeid(*a2) == typeid(B)) << endl; // -> 1 <-- CHANGED
    cout << (typeid(*b) == typeid(B)) << endl; // -> 1
}

多态类的实例存储其最多的动态类型

Instances of a polymorphic class store the dynamic type of their most derived object at runtime.

,并且指向A类型的对象,但是该对象只是类型B的最大派生对象的基类子对象。您想要获得的是当查询 a2 时,这个最导出的对象B的类型。这样你需要一个多态类。)

(In your example a2 is of type pointer-to-A, and is pointing at an object of type A, however this object is only a base class subobject of the most dervived object of type B. What you want to get is the type of this most derived object B when querying a2. For this you need a polymorphic class.)

如何多态类支持最导出的对象的 dynamic_cast typeid (以及虚函数分派)。

That is how polymorphic classes support dynamic_cast and typeid of the most derived object (as well as virtual function dispatch).

非多态类不具有此信息,因此它们只能报告编译时已知的静态类型。非多态类比多态类更紧凑和有效。这就是为什么不是所有的C ++类都是多态的。语言让程序员选择性能和功能之间的权衡。例如:

Non-polymorphic classes do not have this information, so they can only report the static type known at compile-time. Non-polymorphic classes are more compact and efficient then polymorphic classes. That is why not all C++ classes are polymorphic. The language leaves it up to the programmer to chose the tradeoff between performance and functionality. For example:

struct X { int x; };
struct Y : X {};
struct Z : Y {};

在我的系统上,非多态性 Z sizeof(Z)== 4个字节,与 int 相同。

On my system non-polymorphic Z is sizeof(Z) == 4 bytes, same as an int.

struct X { int x; virtual ~X() {}; };
struct Y : X {};
struct Z : Y {};

现在在 Z c $ c> sizeof(Z)== 16个字节。因此,Z的数组现在大300%,因为每个 Z 实例必须在运行时存储其类型信息。

Now after making Z polymorphic, sizeof(Z) == 16 bytes. So an array of Z is now 300% larger, because each Z instance has to store its type information at runtime.

这篇关于在C ++ 11中检查对象类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆