从子类调用父类虚函数
call parent virtual function from child class
我想用两个"单位"做一些"决斗"。我写由两个"单位"构成的"决斗"类。但有些"单位"是特殊的(继承自单位),如英雄、boss等。他们想在战斗中使用特殊打击。但实际上职业"决斗"并不知道谁是英雄,谁是纯单位。
代码如下:
#include <iostream>
class unit{
public:
unit(){};
virtual void make_hit(){
std::cout<<"pure hitn";
}
};
class hero:public unit {
public:
hero():unit(){};
void make_hit(){
std::cout<<"SUPER hitn";
}
};
class duel {
unit *a, *b;
public:
duel(unit _a, unit _b):a(&_a),b(&_b){};
void start (){
a->make_hit();
b->make_hit();
}
};
int main(){
duel(unit(),hero()).start();
return 0;
}
我有两个主要问题。
首先-我使用在构造函数中引用临时对象。当决斗::决斗()结束时,对象是非法的。
秒-我的英雄变成了纯单位,并且不使用"SUPER hit"
是否有可能以优雅的方式修复它(不改变main()
中的调用)?
由于切片,最好总是将多态性与智能指针。这是一种可能的设计:
#include <iostream>
#include <memory>
#include <utility>
using namespace std;
class unit_base
{
public:
virtual ~unit_base() = default;
virtual void make_hit() =0;
};
class unit : public unit_base
{
public:
unit() = default;
virtual void make_hit() override
{
cout << "pure hit" << endl;
}
};
class hero : public unit_base
{
public:
hero() = default;
virtual void make_hit() override
{
cout << "SUPER hit" << endl;
}
};
class duel
{
public:
duel( shared_ptr<unit_base> a, shared_ptr<unit_base> b )
: a(a), b(b)
{}
void start()
{
auto aa = a.lock();
auto bb = b.lock();
if( aa && bb )
{
aa->make_hit();
bb->make_hit();
} else {
cout << "duelist expired" << endl;
}
}
private:
weak_ptr<unit_base> a, b;
};
int main()
{
// use with temporarys
duel{ make_shared<unit>(), make_shared<hero>() }.start();
cout << "-------------" << endl;
// use with variables
auto u = make_shared<unit>();
auto h = make_shared<hero>();
duel d{h,u};
d.start();
cout << "-------------" << endl;
// try to use with expired duelists
u.reset();
d.start();
}
还要记住在基类中总是有一个虚析构函数
In
duel(unit _a, unit _b):a(&_a),b(&_b){};
在按值传递时对对象进行切片。要解决这个问题,可以在构造函数
中引入指针。duel(unit* _a, unit* _b):a(_a),b(_b){};
然后你需要改变main()
来创建对象并将它们传递给duel
int main(){
unit npc;
hero bob;
duel d(&npc,&bob);
d.start();
return 0;
}
我在c++中找到的唯一方法是在"决斗"类中构造函数的所有组合。这个解决方案不是那么优雅,需要在添加新类时修改"决斗"代码,而且这也有开销。
~duel(){
delete a;
delete b;
}
#define _cc(t1, t2) duel(t1 _a, t2 _b) : a(new t1 (_a)), b (new t2(_b)){}
_cc(unit,unit);
_cc(hero,unit);
_cc(unit,hero);
_cc(hero,hero);
#undef _cc
我也试过使用模板,但我找不到一种方法,使自动类型确定
相关文章:
- 父类的私有函数会导致对具有相同名称和相似参数的子类中的公共函数的不明确调用
- 两个父类的构造函数的序列
- C++调用使用重写函数的父类函数
- 在父类中公开受保护的构造函数
- 从父类的向量访问子类函数,而无需向下转换
- 将派生类的构造函数声明为父类的友元
- 如何从子类的构造函数初始化父类的私有成员
- 具有纯虚函数和指针数组对象类型的父类的指针数组
- 在父类函数中创建子类 - 可能吗?
- 调用父类函数来比较父类和子类
- 从多重继承中的派生类函数调用适当的父类函数
- 是否有 lint 工具可以检查子类虚拟函数是否与父类定义匹配?
- 无法使父类的虚拟函数正常工作
- 重写子类构造函数中的父类变量
- 构造函数将父类作为参数
- 父类有 26 个构造函数重载.如何在不复制+粘贴 26 个重载的情况下将一个小任务附加到所有构造器?
- 如果不手动完成,子类是否继承父类的析构函数?
- 当函数返回类型为父类时,如何返回子类的对象?
- 将子类的成员函数强制转换为父类
- 如何将 std::unique_ptr<Parent> 与具有受保护虚拟析构函数的只读父类一起使用