了解 C++ 中的继承和多态性
Posted
技术标签:
【中文标题】了解 C++ 中的继承和多态性【英文标题】:Understanding inheritence and polymorphism in C++ 【发布时间】:2018-02-28 18:28:46 【问题描述】:假设我们有以下继承类。
class A
public:
void virtual show()
cout << "I am A\n";
;
class B:public A
public:
void show()
cout << "I am B\n";
;
class C:public B
public:
void show()
cout << "I am C\n";
;
int main()
A *obj = new C();
obj->show();
return 0;
不创建任何其他对象,如何调用B类的show()函数???
我知道的一种方法是将 C 类中的 show() 修改为,
void show()
B::show();
cout << "I am c\n";
这将首先调用 B 的 show 函数,然后打印“I am C”。但我根本不希望 C 中的 show() 被执行。我希望 B 的 show() 直接执行。
有可能吗?我们可以使用铸造或其他东西来做到这一点吗?
请记住,除了已经创建的对象(即 main() 中的 C)之外,我不允许创建任何其他对象。 今天面试时被问到这个问题。
谢谢!
【问题讨论】:
只要在C班拿出表演,你就可以得到B的表演 没有任何迹象表明obj
是B
,这意味着您无法知道它有void B::show()
。如果你知道你需要obj
是一种B
,那么它应该是一个指向B
的指针。这似乎是一个设计错误。
“被直接执行”是什么意思?它不会打印“我是 C”,或者它必须完全绕过 C::show() 调用而只调用 B::show()?
我仍然对目的感到困惑。不假设继承链中有B
,必须对其进行测试,这意味着类似于B *bptr = dynamic_cast<B*>(obj); if (bptr) bptr->B::show();
。如果您可以假设 B
被楔入某处,那么它会变得相当容易。
@MuzahirHussain 如果在采访中被问到这个问题,我会首先问“为什么?”。似乎问题是要求实现设计错误的解决方案,而正确的解决方案是修复设计,而不是实现。
【参考方案1】:
您可以通过指定类来强制静态调度:
int main()
A *obj = new C();
static_cast<B*>(obj)->B::show();
return 0;
但是如果你想使用这个方法,你必须确定该对象确实是一个B
实例,否则它是未定义的行为。
【讨论】:
这假设我们知道obj
是B
的一种。在这种情况下很清楚,但它并不普遍适用。
我认为它不需要是通用的,只需在这种特定情况下工作。另外,你不能只做obj->B::show()
并完全跳过static_cast
吗?
@Daniel obj
是一个A*
并且A
没有void B::show()
,即使在这种情况下动态类型会有它。
@FrançoisAndrieux 我在答案中添加了一些额外的注释。我认为没有通用的方法可以做到这一点。
@liliscent 你可能会写if(B *b = dynamic_cast<B*>(obj)) b->B::show()
,只有当obj 是B
或更高时才会执行以上是关于了解 C++ 中的继承和多态性的主要内容,如果未能解决你的问题,请参考以下文章
深入了解C++ (13) | 走近vtprvtbl,揭秘动态多态