继承是面向对象的三大特性之一
例如我们看到很多网站中,都有公共的头部,公共的底部,甚至公共的左侧列表,只有中心内容不同
接下来我们分别利用普通写法和继承的写法来实现网页中的内容,看一下继承存在的意义以及好处
class 子类 : 继承方式 父类
普通实现:
#include<iostream>
using namespace std;
//普通实习页面
class Java{
public:
void header(){
cout << "首页、公开课、登陆、注册...(公共头部)" << endl;
}
void footer(){
cout << "帮助中心、交流合作、站内地图...(公共底部)" << endl;
}
void left(){
cout << "Java、Python、C++...(公共分类列表)" <<endl;
}
void content(){
cout << "Java学科视频" << endl;
}
};
class Python{
public:
void header(){
cout << "首页、公开课、登陆、注册...(公共头部)" << endl;
}
void footer(){
cout << "帮助中心、交流合作、站内地图...(公共底部)" << endl;
}
void left(){
cout << "Java、Python、C++...(公共分类列表)" <<endl;
}
void content(){
cout << "Python学科视频" << endl;
}
};
void test01(){
cout << "Java下载视频页面如下:" << endl;
Java ja;
ja.header();
ja.footer();
ja.left();
ja.content();
}
void test02(){
cout << "Python下载视频页面如下:" << endl;
Python py;
py.header();
py.footer();
py.left();
py.content();
}
int main(){
test01();
cout << "------------------------------" << endl;
test02();
return 0;
}
继承实现:
#include<iostream>
using namespace std;
//公共页面
class BasePage{
public:
void header(){
cout << "首页、公开课、登陆、注册...(公共头部)" << endl;
}
void footer(){
cout << "帮助中心、交流合作、站内地图...(公共底部)" << endl;
}
void left(){
cout << "Java、Python、C++...(公共分类列表)" <<endl;
}
};
//Java页面
class Java : public BasePage{
public:
void content(){
cout << "Java学科视频" << endl;
}
};
//Python页面
class Python : public BasePage{
public:
void content(){
cout << "Python学科视频" << endl;
}
};
void test01(){
cout << "Java下载视频页面如下:" << endl;
Java ja;
ja.header();
ja.footer();
ja.left();
ja.content();
}
void test02(){
cout << "Python下载视频页面如下:" << endl;
Python py;
py.header();
py.footer();
py.left();
py.content();
}
int main(){
test01();
cout << "------------------------------" << endl;
test02();
return 0;
}
?
语法:class 子类 : 继承方式 父类
继承方式一共有三种:
#include<iostream>
using namespace std;
//公共继承
class Base1{
public:
int m_A;
protected:
int m_B;
private:
int m_C;
};
class Son1 : public Base1{
public:
void func(){
m_A = 10;
m_B = 10; //父类中保护成员,到子类中变为保护权限
//m_C = 10;
}
}
//保护继承
class Son2 : protected Base1{
public:
void func(){
m_A = 10; //父类中公共成员,到子类中变为保护权限
m_B = 10;
//m_C = 10;
}
}
//私有继承
class Son3 : protected Base1{
public:
void func(){
m_A = 10; //父类中公共成员,到子类中变为保护权限
m_B = 10;
//m_C = 10;
}
}
void test01(){
Son1 s1;
s1.m_A = 100;
//s1.m_B = 100;
//s1.m_C = 100;
}
void test02(){
Son2 s2;
s2.m_A = 100;
//s2.m_B = 100;
//s2.m_C = 100;
}
void test03(){
Son3 s3;
s3.m_A = 100;
//s3.m_B = 100;
//s3.m_C = 100;
}
int main(){
test01();
return 0;
}
?
问题:从父类继承过来的成员,哪些属于子类对象中?
#include<iostream>
using namespace std;
class Base{
public:
int m_A;
protected:
int m_B;
private:
int m_C;
};
class Son : public Base{
public:
int m_D;
};
void test01(){
//父类中所有非静态成员属性都会被子类继承下去
//父类中私有成员属性,是被编译器给隐藏了,因此是访问不到的,但是确实被继承下去了
cout << "size of Son = " << sizeof(Son) << endl;
}
int main(){
test01();
return 0;
}
?
子类继承父类后,当创建子类对象,也会调用父类构造函数
问题:父类和子类的构造和析构顺序是谁先谁后呢?
#include<iostream>
using namespace std;
class Base{
public:
Base(){
cout << "Base构造函数" << endl;
}
~Base(){
cout << "Base析构函数" << endl;
}
};
class Son : public Base{
public:
Son(){
cout << "Son构造函数" << endl;
}
~Son(){
cout << "Son析构函数" << endl;
}
};
void test01(){
Base b;
Son s;
}
int main(){
test01();
return 0;
}
总结:继承中,先调用父类构造函数,再调用子类构造函数,析构顺序与构造相反
?
问题:当子类与父类出现同名成员,如何通过子类对象,访问到子类或父类中同名的数据呢?
#include<iostream>
using namespace std;
class Base{
public:
Base(){
m_A = 100;
}
void func(){
cout << "Base - func()调用 " << endl;
}
int m_A;
};
class Son : public Base{
public:
Son(){
m_A = 200;
}
void func(){
cout << "Son - func()调用 " << endl;
}
int m_A;
};
void test01(){
Son s;
cout << "m_A = " << s.Base::m_A << endl;
s.Base::func();
}
int main(){
test01();
return 0;
}
总结:
?
问题:继承中同名的静态成员在子类对象上如何进行访问?
静态成员和非静态成员出现同名,处理方式一致
#include<iostream>
using namespace std;
//继承中的同名静态成员处理方式
class Base{
public:
static int m_A;
};
int Base::m_A = 100;
class Son : public Base{
public:
static int m_A;
};
int Son::m_A = 200;
void test01(){
//1.通过对象访问数据
Son s;
cout << "通过对象访问数据" << endl;
cout << "Son下m_A = " << s.m_A << endl;
cout << "Base下m_A = " << s.Base::m_A << endl;
//2.通过类名访问数据
cout << "通过类名访问数据" << endl;
cout << "Son下m_A = " << Son::m_A << endl;
cout << "Base下m_A = " << Son::Base::m_A << endl;
}
int main(){
test01();
return 0;
}
?
C++允许一个类继承多个类
语法:class 子类 : 继承方式 父类1,继承方式 父类2...
多继承可能会引发父类中有同名成员出现,需要加作用域区分
C++实际开发中不建议使用多继承
?
菱形继承概念:
典型的菱形继承案例:
????动物
????↓???????↘
????羊????????驼
????↓???????↙
????羊驼
菱形继承问题:
#include<iostream>
using namespace std;
//动物类
class Animal{
public:
int m_A;
};
//利用虚继承解决菱形继承的问题
//继承之前加上关键字virtual变成虚继承
//Animal类称为 虚基类
class Sheep : virtual public Animal{
};
class Tuo : virtual public Animal{
};
class SheepTuo : public Sheep, public Tuo{
};
void test01(){
SheepTuo st;
st.Sheep::m_A = 18;
st.Tuo::m_A = 28;
//当菱形继承时,两个父类拥有相同数据,需要加以作用域区分
cout << "st.Sheep::m_A = " << st.Sheep::m_A << endl;
cout << "st.Tuo::m_A = " << st.Tuo::m_A << endl;
cout << "st.m_A = " << st.m_A << endl;
//这份数据我们知道,只要有一份就可以,菱形继承导致数据有两份
}
int main(){
test01();
return 0;
}
虚继承:
总结:
原文:https://www.cnblogs.com/maeryouyou/p/12087826.html