重写返回基类型的函数
Override function that return base type
我有两个类。基类CCD_ 1和派生类CCD_。类Parent
具有返回其类类型的纯虚拟函数。如何在派生类中重写它?
class Parent
{
public:
virtual Parent* OverrideMe(Parent* func) = 0;
};
class Child : public Parent
{
public:
Child* OverrideMe(Child* func) override;
};
我尝试了Child* OverrideMe(Child* func) override;
,但最终出现了一个错误,即它没有覆盖基类成员。
如果C++有完全的协方差和逆变支持,正确的关系将是输入中的逆变和输出中的协变。即:
struct Organism { };
struct Animal : Organism {
virtual Animal* OverrideMe(Animal* ) = 0;
};
struct Dog : Aniaml {
Dog* OverrideMe(Organism* ) override { ... }
↑↑↑ ↑↑↑↑↑↑↑↑
covariant contravariant
};
这看起来有点不直观,但确实有道理。如果您期望一个Animal*
,那么您应该能够处理任何属于Animal*
(Dog*
符合条件)的内容。相反,如果你在Animal*
上做一些运算,你只需要一个可以取Animal*
的运算,而取Parent
0的运算在这方面是合格的。
请注意,如果输入是co变体,则会破坏类型系统。考虑类似的事情;
Animal* a = new Dog;
a->OverrideMe(new Cat);
如果Dog::OverrideMe
被允许接受Dog*
,那将失败——Cat*
不是Dog*
!所以可以乘坐Animal*
。。。或者任何比这更通用的东西(例如Organism*
),因为所有这些都可以正常工作。
C++不支持输入中的逆变,只支持输出中的协方差。所以你可以写:
Dog* OverrideMe(Animal* ) override { ... }
或:
Animal* OverrideMe(Animal* ) override { .... }
但没有别的。
函数参数的类型和函数的cv限定符必须相同。所以你可以使用
Child* OverrideMe(Parent* func) override;
您没有在这里重写,因为您的OverrideMe
函数与您试图重写的基类中的函数不接受相同的参数:
class Parent
{
public:
virtual Parent* OverrideMe(Parent* func) = 0;
};
class Child : public Parent
{
public:
virtual Child* OverrideMe(Parent* func) override;
};
这"闻起来很臭",换句话说,你正在"打破"正常的"任何对象都应该被派生的任何其他对象替换"。
如果基类中有一个接口函数,那么该函数在整个类层次结构中应该采用相同的类型。
所以正确的做法是:
Parent*OverrideMe(Parent*func)覆盖;
(正如juancopanza所说,你可以返回一个派生类型,但你确定父返回的值总是同一个类吗?对我来说,这看起来像是可能返回"任何派生对象"的函数类型,在这种情况下,你要么撒谎,要么得到"有趣的效果")
如果由于某种原因,这在您的情况下实际上不起作用,那么您可能不应该以这种方式使用继承。
- 为什么在我的函数类型后使用引用运算符 (&) 允许我修改它返回的值?
- 来自 DLL 的函数调用 [表观调用的括号前面的表达式必须具有(指向-)函数类型]
- 是否有任何建议来统一函数类型限定符并简化可恶的函数类型?
- 关于 C++ 中的函数类型定义
- 用于检测函数类型是否为否的特征
- 函数类型参数的模板参数推导
- 标准对此指向成员函数类型模板参数有何说明?是我的代码有误,还是 MSVS 16.6 有问题?
- C++无效的函数类型转换
- STL 函数和函数类型与函数指针类型
- 如何将result_of与函数类型定义一起使用
- 将模板(没有规范)传递给 std::thread() 会出现错误:<未解析的重载函数类型>匹配错误
- C++ 编译错误:gnu_printf是无法识别的格式函数类型
- 专门用于"direct"函数类型(与函数指针类型相对)
- 将函数类型作为模板参数传递不会编译
- 通过参数传递 lambda(无函数类型模板)
- 如何在模板参数中分离函数类型返回类型和参数
- 为什么比较函数类型需要指定为模板参数?
- 带有限定符的函数类型定义用例
- 如何声明对函数类型的常量引用
- 非类型模板参数允许各种函数类型?