【问题标题】:What do I need to do in order to ask, if an pointer to an abstract class in instance of a child class?我需要做什么才能询问是否指向子类实例中的抽象类的指针?
【发布时间】:2019-09-28 10:39:30
【问题描述】:

我需要一些帮助才能正确理解所有内容。

我想检查一个指向抽象类的指针是否是特定子类的实例。

我有一个抽象类“kunde”和两个继承kunde方法的子类“firmenkunde”和“privatkunde”。

为了通过“int knr”(int customer number)搜索,我使用指向“kunde”的指针作为返回类型。

在数据库类中,我取回“kdstatus”并使用

kunde * kd = new privatkunde(0);

如果状态是 PK 或 new Firmenkunde(0) 如果它是 FK。 抽象类 kunde 没有任何我可以用来保存状态的属性。

通过这种方式,我确实希望能够询问返回的指针是否是类 privatkunde 或 Firmenkunde 的实例。但是我没有找到任何方法来做到这一点。

 MessageBox::Show(marshal_as<String^>(typeid(kd).name())); 

我确实询问了 typeid 名称,但这只会返回“class kunde *”,这不是我想知道的。

有没有办法解决这个问题?

【问题讨论】:

  • 这不是 C++。
  • 看看virtual函数。
  • 请问什么不是 C++?您的意思是 MessageBox 这是来自 .Net,因为我们使用 Windows 窗体作为 gui
  • 在基类中添加一个变量(比如ID);每个子类的 ID 不同。

标签: class object pointers c++-cli instanceof


【解决方案1】:

通常您可以为此使用dynamic_cast

一个例子:

class Parent
{
public:
    virtual ~Parent();

    virtual void do_thing()= 0;
};

class Child1: public Parent
{
public:
    void do_thing() override
    {
        //...
    }
};

class Child2: public Parent
{
public:
    void do_thing() override
    {
        //...
    }
};

void use_parent(Parent* p)
{
    auto c1_ptr = dynamic_cast<Child1*>(p);
    if(c1_ptr != nullptr)
    {
        // p is a Child1

        do_thing_with_child1(c1_ptr);

    }
    auto c2_ptr = dynamic_cast<Child2*>(p);
    if(c2_ptr != nullptr)
    {
        // p is a Child2
        do_thing_with_child2(c2_ptr);
    }
}

虽然这可行,但如果您有多个子类,则很难维护。您必须记住为您定义的每个新子类添加一个案例。

在设计面向对象的系统时,更好的方式是使用“告诉,不要问”的概念。可以在here 找到有关此概念的精彩文章。

【讨论】:

  • 我猜是拼写错误,但动态转换的语法有点不对,还要注意动态转换需要 rtti。
  • 好的,我明白我需要子类中的方法来解决我的问题是正确的吗?
  • 但是如何调用子方法呢?如果我是正确的,我不能从父母的指针调用孩子的方法。
  • dynamic_cast&lt;T*&gt;得到的指针是T*类型的。因此,您可以在从转换获得的指针上调用该方法。
【解决方案2】:

您可以使用typeid,正如您所提到的。使用多态性,您可以编写:

kunde * kd = new privatkunde(0);
if(typeid(kd) == typeid(privatkunde))
{
    // This is a privatkunde objet
}

请参阅here 以获得更多解释。

您遇到的问题是您的kunde 类不是多态的。正如@George 评论的那样,看看虚拟方法是如何工作的。

希望对你有帮助。

【讨论】:

  • 但是 typeid(kd).name 返回 class kunde * 即使我认为它应该是 privatkunde *
  • 是的,因为您没有使基类多态。检查我给你的链接,有一个很好的例子。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-06-17
  • 1970-01-01
  • 2013-01-27
  • 2015-07-28
  • 1970-01-01
相关资源
最近更新 更多