如何将派生对象传递给C ++中的类?

时间:2018-05-30 14:43:08

标签: c++ inheritance polymorphism

我认为我误解了C ++继承的东西。

假设我有这种经典继承:

    class A{
    public: 
        virtual void method1() =0;
        virtual ~A() = default;
    }

    class B : public A{
    public :
        void method1(){doSomething();}
    }

    class C : public A{
    public :
        void method1(){doSomethingElse();}
    }

如何让其他Q类拥有B或C类型的对象,而不事先知道它是哪种类型? (我的意思是我们知道它是A型的全部)

感谢阅读!

2 个答案:

答案 0 :(得分:5)

由于您不希望Q了解BC,因此您必须通过指针间接存储A,因为您无法知道存储空间BC或尚未知的派生类D将需要。动态分配并由Q拥有的单个对象的经典解决方案是std::unique_ptr

由于std::unique_ptr默认使用delete删除对象,因此您还需要在A中使用虚拟析构函数。

#include"A.hpp"
#include<memory>

class Q {
    std::unique_ptr<A> a;
public:
    Q(std::unique_ptr<A> ai) : a{std::move(ai)} {}
};

如果您不想通过A独占所有Q,或者不想提供虚拟析构函数,您也可以使用std::shared_ptr。共享指针动态记住存储的类,因此如果它们被适当地创建,则会正确地销毁对象,特别是使用std::make_shared<MostDerivedClass>。它们也使用引用计数,并且只有在对对象的所有引用都消失后才会删除对象。 与std :: unique_ptr相比,缺点是需要一些额外的内存和一些运行时成本,与普通指针相比,它通常没有开销。

答案 1 :(得分:3)

类必须确切知道其所有子对象的类型。动态多态性只能通过间接来实现。因此,虽然包含多态类型的对象是不可能的,但是可以拥有一个。例如:

struct Q {
    shared_ptr<A> object; // could point to B or C
}