复制对象 - 保持多态性

2022-01-24 00:00:00 inheritance pointers polymorphism c++

以下代码尝试复制对象并保留原始类型.不幸的是,它不起作用(每个复制的对象都将成为 Super 而不是与其原始对象属于同一类).

The following code tries to copy an object and keep the original type. Unfortunately it does not work (every copied object will become a Super instead of being of the same class as its original).

请注意 copySuper(const Super& givenSuper) 不应该知道 Super 的子类.

Please note that copySuper(const Super& givenSuper) should not know anything about the subclasses of Super.

可以做这样的副本吗?还是我必须更改 copySuper 的定义?

Is it possible to do such a copy? Or do I have to change the definition of copySuper ?

#include <string>
#include <iostream>

class Super
{
public:
    Super() {};
    virtual ~Super() {};

    virtual std::string toString() const
    {
        return "I'm Super!";
    }
};

class Special : public Super
{
public:
    Special() {};
    virtual ~Special() {};

    virtual std::string toString() const
    {
        return "I'm Special!";
    }
};

Super* copySuper(const Super& givenSuper)
{
    Super* superCopy( new Super(givenSuper) );
    return superCopy;
}

int main()
{
    Special special;
    std::cout << special.toString() << std::endl;

    std::cout << "---" << std::endl;

    Super* specialCopy = copySuper(special);
    std::cout << specialCopy->toString() << std::endl;

    return 0;
}

//Desired Output:
// # I'm Special!
// # ---
// # I'm Special!
//
//Actual Output:
// # I'm Sepcial!
// # ---
// # I'm Super!

推荐答案

试试这个:

class Super
{
public:
    Super();// regular ctor
    Super(const Super& _rhs); // copy constructor
    virtual Super* clone() const {return(new Super(*this));};
}; // eo class Super


class Special : public Super
{
public:
    Special() : Super() {};
    Special(const Special& _rhs) : Super(_rhs){};
    virtual Special* clone() const {return(new Special(*this));};
}; // eo class Special

请注意,我们已经实现了一个 clone() 函数,Special(和 Super 的任何其他派生词)覆盖该函数以创建正确的副本.

Note that we have implemented a clone() function that Special (and any other derivative of Super) overrides to create the correct copy.

例如:

Super* s = new Super();
Super* s2 = s->clone(); // copy of s
Special* a = new Special();
Special* b = a->clone(); // copy of a

正如其他评论员指出的那样,*this,而不是 this.这会教我快速打字.

As other commentator pointed out, *this, not this. That'll teach me to type quickly.

另一个更正.

我真的不应该在工作中这么快发帖.为协变返回类型修改了 Special::clone() 的返回类型.

I really should not post so quickly when in the middle of work. Modified return-type of Special::clone() for covariant return-types.

相关文章