在C++多态性中,如何避免函数的名称隐藏(调用错误时没有匹配的函数)



我正在介绍C++类,我正试图找出为什么我会遇到"调用没有匹配的函数"错误。我也看过其他帖子,但这些似乎主要是构造函数本身的问题。

这是简化的片段:

在基本类-船舶

// Members: shipName, shipBuiltYear
Ship::Ship(){ //implementation }
Ship::Ship(string name, string year){ //implementation }
void Ship::set(string name, string year){ //implementation }

衍生类-海盗船

// Members: numPirates
PirateShip::PirateShip() : Ship() { //implementation }
PirateShip::PirateShip(string name, string year, string pirates) : ship(name, year){ //implementation }
void PirateShip::set(int pirates){ //implementation }

在主中

Ship *ships[2] = {new Ship(), new PirateShip()};
ships[0] -> set("Luvinia", "2020"); // using setter from base class
ships[1] -> set("Skylin", "2030"); // using setter from base class
ships[1] -> set(100); // using setter from derived class

问题是你不能用基类设置海盗船,然后用海盗船再次设置吗?

我必须换吗:

void PirateShip::set(int pirates){ //implementation }

至:

void PirateShip::set(string name, string year, string pirates)
{ 
Ship::set(name, year);
numPirates = pirates; 
}

或者有其他方法可以做到这一点吗?

这里有两个问题。

第一:

Ship *ships[2] = {new Ship(), new PirateShip()};

这是指向两个对象的CCD_ 1部分的指针数组。第一个是一个Ship,第二个是PirateShip。但是你只有一个指向PirateShipShip部分的指针,所以只能(直接(与它交互

如果Ship有虚拟方法,那么您可以使用RTTI和dynamic_cast来查询给定的Ship*是否指向Ship0的Ship部分,如下所示:

auto* pirate = dynamic_cast<PirateShip*>(some_ship);

如果pirate不为空,则some_ship指向PirateShipShip段。

请注意,使用动态强制转换是代码气味;这可能意味着您应该改进基类接口,或者在这里没有指向基类的指针。


第二部分是,如果你想从PirateShip*调用Ship::set,你需要添加

using Ship::set;

至CCD_ 17的主体。

如果知道元素是特定类型(并且必须知道如果使用其特定参数要求进行调用(,则可以强制转换为适当的类型:

Ship* ships[2] = {new Ship(), new PirateShip()};
ships[0] -> set("Luvinia", "2020"); // using setter from base class
ships[1] -> set("Skylin", "2030"); // using setter from base class
dynamic_cast<PirateShip*>(ships[1]) -> set(100); // change to the correct interface

然而,我会质疑这里的设计。为了使多态性正常工作,您不需要知道创建后子类的确切类型。

也许将初始化调用作为构造函数的一部分?或者在将对象添加到数组之前配置对象

现在,使用指向自己的对象的原始指针被认为不是一种好做法。我推荐智能指针:

std::unique_ptr<Ship> ships[2];

同样,在大多数情况下,使用内置阵列也不太理想。考虑std::vector:

std::vector<std::unique_ptr<Ship>> ships;

或者如果你想要固定大小的std::array

std::array<std::unique_ptr<Ship>, 2> ships;

最新更新