什么是子类型
花木兰替父从军
公有继承时,派生类的对象可以作为基类的对象处理,派生类是基类的子类型。
例:
#include <iostream>
using namespace std;
class A {
public:
A() {}
~A() {}
void kill() { cout << "A kill." << endl;}
};
class B : public A {
public:
B() {}
~B() {}
void kill() {cout << "B kill." << endl;}
};
void test(A a) {
a.kill(); // 都是调用父类A的kill方法
}
int main(void) {
A a;
B b;
test(a);
test(b);
system("pause");
return 0;
}
运行截图:
花木兰可以替父从军,父亲却无法替木兰从军
子类可以调用父类的方法,父类却无法调用子类的方法
例:
#include <iostream>
using namespace std;
class A {
public:
A() {}
~A() {}
void kill() { cout << "A kill." << endl;}
};
class B : public A {
public:
B() {}
~B() {}
void kill() {cout << "B kill." << endl;}
};
void test(A a) {
a.kill();
}
void test2(B b) {
b.kill();
}
int main(void) {
A a;
B b;
test(a); // 调用父类A的kill方法
test(b); // 调用父类A的kill方法
test2(b); // 调用子类B自己的kill方法
//test2(a); // error 父类无法调用子类的kill方法
system("pause");
return 0;
}
运行截图:
子类型关系具有单向传递性:
C类是B类的子类型
B类是A类的子类型
=
=
=
子类型的作用
在需要父类对象的任何地方, 可以使用”公有派生”的子类的对象来替代,
从而可以使用相同的函数统一处理基类对象和公有派生类对象
即:形参为基类对象时,实参可以是派生类对象
#include <iostream>
#include <sstream>
using namespace std;
class Father {
public:
void play() {
cout << "KTV唱歌!" << endl;
}
};
class Son : public Father {
public:
void play() {
cout << "今晚吃鸡!" << endl;
}
};
void party(Father *f1, Father *f2) {
f1->play();
f2->play();
}
int main(void) {
Father yangKang;
Son yangGuo;
party(&yangKang, &yangGuo);
system("pause");
return 0;
}
执行后都是调用父类的play方法
运行截图:
注意:如果把Son改为protected继承,或private继承,就会导致编译失败!
=
=
=
子类型的应用
-
基类(父类)的指针,可以指向这个类的公有派生类(子类型)对象。
Son yangGuo;
Father * yangKang = &yangGuo; -
公有派生类(子类型)的对象可以初始化基类的引用
Son yangGuo;
Father &yangKang = yangGuo; -
公有派生类的对象可以赋值给基类的对象
Son yangGuo;
Father yangKang = yangGuo;
注意:以上的应用,反过来就会编译失败!