c++-继承的学习

0
10

继承的基本概念

  • 继承和派生

    • 继承概念
    • 派生类的访问控制(继承三种方式、类三种访问控制、三看原则)综合训练
    • 继承中的构造和析构
      • 类型兼容性原则
      • 继承中的构造和析构
      • 继承中同名成员函数、成员变量处理方法
      • 继承中的static关键字
  • 继承概念

  • 派生类的访问控制(继承三种方式、类三种访问控制、三看原则)综合训练

  • 继承中的构造和析构

    • 类型兼容性原则
    • 继承中的构造和析构
    • 继承中同名成员函数、成员变量处理方法
    • 继承中的static关键字
  • 多继承概念

  • 多继承

    • 多继承概念
    • 二义性
    • 虚继承基本实验原理
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <string>

using namespace std;


class Student
{
public:
	Student()
	{

	}
	Student(int id, string name)
	{
		this->id = id;
		this->name = name;
	}

	void printS() {
		cout << "id = " << this->id << ", name = " << this->name << endl;
	}
	int id;
	string name;
};

//创建一个新的学生类,增加score、功能
class Student2
{
public:
	Student2(int id, string name, int score)
	{
		this->id = id;
		this->name = name;
		this->score = score;
	}

	void printS() {
		cout << "id = " << this->id << ", name = " << this->name << endl;
		cout << "score = " << this->score << endl;
	}
private:
	int id;
	string name;

	//add
	int score;
};


//通过继承创建一个新的学生类
class Student3 :public Student
{
public:
	Student3(int id, string name, int score) :Student(id, name)
	{

		this->score = score;
	}

	void printS() {
		Student::printS();
		cout << "score = " << this->score << endl;
	}
private:
	int score;
};


int main(void)
{
	Student3 s3(1, "zhang3", 80);

	s3.printS();


	return 0;
}

继承的方式

  • 规则1, 只要是父类中的private成员,不管是什么继承方式,儿子都访问不了

  • 规则2, 如果是公有(public)继承, 儿子中的访问控制权限保持不变。

  • 规则3, 如果是保护(protected)继承, 儿子中父亲中除了private成员,其余在儿子中都是protected

  • 规则4, 如果是私有(private)继承, 儿子中的父亲的除了private成员,其余在二中都是private成员。

  • 三看原则:

    • 看调用的成员变量是在类的内部还是类的外部
    • 看儿子继承方式,
    • 当前变量在儿子中的变量在父亲中的访问控制权限
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <memory>

using namespace std;



class Parent
{
public:
	int pub; //在类的内部 和 外部 都能访问。
protected:
	int pro; //在类的内部可以访问, 在类的外部不可以访问
private:
	int pri;  //在类的内部可以访问, 在类的外部不可以访问
};

//公有继承
class Child :public Parent
{
public:
	void func()
	{
		cout << pub << endl; //pub父类的public成员变量,在public继承 类的 【内部 外部】可以访问。

		cout << pro << endl;//pro 是父类protected成员变量 在public继承类的 【内部】可以访问。外部访问不了 
		                    //此时的pro在孙子能够访问,说此时pro不是private成员,而是protected成员

		//cout << pri << endl; //pri 是父类private成员变量 在public继承类的 【内部,外部】[不]可以访问。
	}

};

//孙子类
class SubChild : public Child
{
	void sub_func()
	{
		cout << pro << endl;
	}
};


//保护继承
class Child2 :protected Parent
{
public:
	void func2() {
		pub;//此时pub通过protected继承 能够在类的内部访问。 
			//pub 在类的内部可以访问, 类的外部访问不了, 类的儿子可以访问
			//pub 就是protected成员
		pro;//pro 根pub 是一样的性质,pro也是protected成员
		//pri;
	}
};

class Sub_child2:public Child2
{
public:
	void sub_func2() {
		pub;
		pro;
	}
};

//私有继承
class Child3 :private Parent
{
public:
	void func3()
	{
		pub;//pub 在类的内部可以访问。在类的内部可以访问,类的外部不能访问。
		    //pub 在儿子中访问不了,说明pub在Child3中是 私有成员
		pro;//pro 根pub的性质是一样, 也是私有成员。
		pri;
	}
};

class Sub_Child3 :public Child3
{
public:
	void sub_fun3()
	{
		pub;
		pro;
	}
};



int main(void)
{
	Child c1;
	c1.func();

	c1.pub;
	//c1.pri;

	//Child2 c2;
	//c2.pub;
	//c2.pro;
	
	Child3 c3;
	//c3.pub;
	//c3.pro;

	Child2 c2;
	c2.pub;
	c2.pro;

	c1.pub;
	

	return 0;
}

继承方式的练习

#include	 <iostream>
using namespace	std;


class	A
{
private:
	int	a;
protected:
	int	b;
public:
	int	c;
	A()
	{
		a = 0;
		b = 0;
		c = 0;
	}
	void	set(int	a, int	b, int	c)
	{
		this->a = a;
		this->b = b;
		this->c = c;
	}
};

class	B : public	A
{
public:
	void	print()
	{
		//cout << "a	=	" << a;				 //a是父类的私有成员访问不了
		cout << "b	=	" << b;				 //b 此时是保护成员,类的内部可以访问
		cout << "c	=	"<<c << endl;			//c 此时是公有成员,类的内部可以访问
	}
};

class	C : protected	A
{
public:
	void	print()
	{
		//cout << "a	=	" << a;				 //a是父类的私有成员访问不了
		cout << "b	=	" << b;				 //b 在子类中是protected权限,类的内部可以访问。
		cout << "c	=	" <<c << endl;	 //c 子类的protected成员,类的内部可以访问。
	}
};

class	D : private	A
{
public:
	void	print()
	{
		//cout << "a	=	" << a;					//a是父类的私有成员访问不了
		cout << "b	=	" << b << endl;		 //b 此时是private成员,类的内部可以访问。
		cout << "c	=	" << c << endl;		 //c 此时是private成员,类的内部可以访问。
	}
};

int	main(void)
{
	A	aa;
	B	bb;
	C	cc;
	D	dd;
	aa.c = 100;					 //c 是公有 ,类的外部可以访问。
	bb.c = 100;					 //Bpublic 继承与A ,保持权限不变,c 是公有, 类的外部可以访问
	//cc.c = 100;					 //C protected 继承与A, c 在此类中是protected成员,类的外部不能访问。
	//dd.c = 100;					 //D private 继承与A, c在此类中private成员,类的外部不能访问。
	aa.set(1, 2, 3);			//能否访问???
	bb.set(10, 20, 30);			//能否访问???
	//cc.set(40, 50, 60);			//能否访问???
	//dd.set(70, 80, 90);			//能否访问???

	bb.print();					 //print 是定义在B类 public成员函数,在类的外部可以访问。
	cc.print();					 //print 是定义在C类 public成员函数,在类的外部可以访问。
	dd.print();					 //print 是定义在D类 public成员函数,在类的外部可以访问。

	return 0;
}

类的兼容性复制原则

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>


using namespace std;

/*
	子类对象可以当作父类对象使用。
	子类对象可以直接赋值给父类对象。
	子类对象可以直接初始化父类对象.
	****父类指针可以直接指向子类对象***
	父类引用可以直接引用子类对象
*/

class Parent
{
public:
	void printP() {
		cout << "a " << this->a << endl;
	}
	int a=333;
};

class Child :public Parent
{
public:
	void printC()
	{
		cout << "b = " << this->b << endl;
	}
	int b;
};


void myPrint(Parent *pp)
{
	pp->printP();
}

int main(void)
{
//	Parent p;

//	Child c = p; //p对象填充不满c对象空间,

//	Child c;

//	Parent p = c;//c 对象所占用的内存空间 >= p对象占用空间 能够填充满p对象所需要空间。

//	p = c;

//	c.printP(); //c 能够当做父类 p 来使用。

	Parent *pp = NULL;//父类指针
	Child *cp = NULL;//子类指针
	

	Parent p;//父类对象
	Child c; //子类对象

	

	pp = &c;//c 内存布局能够满足父类指针的全部需求, 可以用一个儿子的对象地址给父类指针赋值。
	
	myPrint(&p);
	myPrint(&c);

	return 0;
}

子类的构造和析构

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>


using namespace std;

class Parent
{
public:
	Parent()
	{
		cout << "Parent().." << endl;
		a = 0;
	}
	Parent(int a) {
		cout << "Parent(int)..." << endl;
		this->a = a;
	}
	~Parent(){
		cout << "~Parent" << endl;
	}
	int a;
};

class Child :public Parent
{
public:
	//在调用子类的构造函数时候,一定会调用父类的构造函数
	// 父类先构造,子类后构造。
	Child(int a, int b) :Parent(a)
	{
		cout << "Child(int, int)..." << endl;
		this->b = b;
	}

	void printC() {
		cout << "b = " << b << endl;
	}

	~Child(){
		cout << "~Child()..." << endl;
	}

	int b;
};

int main(void)
{
	Child c(10, 20);

	c.printC();
	
	return 0;
}

子类与父类的变量名相同

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>


using namespace std;


class Parent
{
public:
	Parent(int a) {
		this->a = a;
	}

	int a;
};

class Child :public Parent
{
public:
	Child(int p_a, int c_a) :Parent(p_a)
	{
		this->a = c_a;
	}

	void print()
	{
		cout << Parent::a << endl;
		cout << this->a << endl;//child's a
	}
	int a;
};


int main(void)
{
	Child c(10, 100);
	c.print();

	
	return 0;
}

继承中的static

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>


using namespace std;

class A
{
public:
	static int a;
private:

};

class B :public A
{
public:
private:
};

int A::a = 100;//静态成员变量 初始化

int main(void)
{
	A a1;
	A a2;

	cout << a1.a << endl;//100
	cout << a2.a << endl;//100

	A::a = 300;

	cout << a1.a << endl;//300
	cout << a2.a << endl;//300

	B b1;
	B b2;
	A::a = 400;

	cout << "------" << endl;
	cout << b1.a << endl;//400
	cout << b2.a << endl;//400
	cout << a1.a << endl;//400
	cout << a2.a << endl;//400

	return 0;
}

多继承

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>


using namespace std;

//家具类
class Furniture
{
public:
	int m; //材质
};

//将父亲类继承爷爷类  改成虚继承, 防止儿子在多继承我的时候,出现爷爷中的变量会拷贝多份。
class Bed:virtual public Furniture
{
public:
	void sleep() {
		cout << "在床上睡觉" << endl;
	}
};


class Sofa:virtual public Furniture
{
public:
	void sit() {
		cout << "在沙发上休息" << endl;
	}
};

//沙发床
class SofaBed :public Bed, public Sofa
{
public:
	void SleepAndSit() {
		sleep();
		sit();
	}
};

int main(void)
{
	Bed b;
	b.sleep();

	Sofa s;
	s.sit();

	cout << " ------ " << endl;

	SofaBed sb;
	sb.SleepAndSit();

	sb.m = 100;//此时只有一个m
	// sb.Bed::m = 100;
	// sb.Sofa::m = 200;
	
	return 0;
}

<

发布回复

请输入评论!
请输入你的名字