day9.C++多态之虚函数

C++多态之虚函数

1)什么是虚函数

多态性主要通过虚函数(virtual functions)实现,它允许派⽣类重写基类中的⽅

法,从⽽在运⾏时根据对象的实际类型来调⽤相应的函数。

实现原理

c++ 复制代码
#include<iostream> 
#include<string>

using namespace std;



class animal
{
   public:
	virtual void runing()
	{
		
		cout<<"i can run"<<endl;
	}
	
	virtual void talk()
	{
		cout<<" i can talk"<<endl;
	}
	
	
};


//派生类继承了父类,父类中的虚函数 在派生类即使被重写了,该函数仍然是虚函数。
class cat :public animal
{
public:
	virtual void runing() // 派生类中对父类的虚函数进行重新实现,该函数不管加不加virtal关键字修饰,它都是虚函数,一般建议加上。
	{
		cout<<" i can run fast"<<endl;
		
	}
	
	//重写:在派生类中对父类的同名成员函数 进行重新实现, 重载:在同一个作用域下,编写多个同名函数,要确保这些函数要么形参或类型不一样
	virtual void talk()
	{
		cout<<" i can talk by cat language"<<endl;
	}
	
};

class dog :public animal
{
public:
	//在派生类重写父类中虚函数时 加上是一个好习惯。
	virtual void runing() override  //如果派生类中重写的成员函数如果加了这个关键字override修饰,在编译的时候 它会自动取检测父类是否存在该虚函数 如果不存在就报错,如果存在则放行
	{
		cout<<" i can run and jump"<<endl;
		
	}
	
	virtual void talk()override
	{
		cout<<" i can talk by dog language"<<endl;
	}
	
	
};


void test(animal &per) //动态多态是建立在继承的基础之上,没有继承就没有多态。
{
	
	per.runing();
	//per.talk();
	
}


//实现多态的条件:1.需要在基类中定义虚函数 2.在派生类中对父类的虚函数实现重写 3.多态的接口需要用父类的指针或父类的引用类型  4.派生类需要采用公有继承

int main() {

	
	cat s1;
	dog s2;
	
	test(s1);
	test(s2);
	
	/*
	
	不同对象s1,s2 调用相同接口runing()所表现出的不同行为
	i can run fast
	i can run and jump 
	 这个就叫做多态
	*/
	
	return 0;
}
c++ 复制代码
#include<iostream> 
#include<string>

using namespace std;

class bird
{
public:
	virtual void fly() final  //final修饰父类的虚函数,就表示该成员函数不允许在派生类中得到重写。final关键字可以阻断派生类对它所修饰的虚函数进行重写
	{
		
		
		cout<<" i can flying"<<endl;
	}
	
	
	
};

class tuo_bird:public bird
{
public:
//	virtual void fly() 
//	{
//		
//		
//	}
	
	
	
};




int main() {

	
	tuo_bird s1;
	//s1.fly();
	s1.fly();
	

	
	return 0;
}
c++ 复制代码
#include<iostream> 
#include<string>

using namespace std;

class bird
{
public:
	//纯虚函数的定义格式:virtual 返回类型 函数名([形参列表])=0;  特点:它是一个没有函数体的函数,靠派生类来实现
	//抽象类:如果一个类中存在纯虚函数,那么该类就变成了 抽象类
	//抽象类特点:不可以通过抽象类构建对象
	virtual void fly()=0;
	//virtual void myfly()=0;
	
	
	
};

class parrot:public bird  //如果派生类继承了抽象类 如果在派生类中没有对父类中的纯虚函数进行重写,那么该派生类也是抽象类
{
	
public:
	void fly()  //派生类但凡对父类中的任何一个纯虚没有实现 派生类仍然是抽象类
	{
		
		cout<<" i can fly";
	}
	
	
	
};






int main() {


   parrot ss;
   cout<<sizeof(ss);//8 ---一个类中存在虚函数,会造成该类创建的对象 会多占用对象一个指针大小的空间。
	
	return 0;
}
c++ 复制代码
#include<iostream> 
#include<string>

using namespace std;

class bird
{
public:

	virtual void fly()
	{
		cout<<"fly from bird";
	}
	
	virtual ~ bird()
	{
		
		cout<<"bird 析构函数"<<endl;
	}

	
	
};

class parrot:public bird  //如果派生类继承了抽象类 如果在派生类中没有对父类中的纯虚函数进行重写,那么该派生类也是抽象类
{
	
public:
	void fly()  //派生类但凡对父类中的任何一个纯虚没有实现 派生类仍然是抽象类
	{
		
		cout<<" i can fly";
	}
	
	~parrot()
	{
		
		cout<<"parrot"<<endl;
	}
	
	
	
};






int main() {


 //当用父类的指针指向一个派生类对象时,此时 如何对该地址施加一个delete 会造成内存泄漏。
  bird * s1=new parrot;
	
  delete s1;
	
	return 0;
}

菱形继承

c++ 复制代码
#include<iostream> 
#include<string>

using namespace std;


//菱形继承:会造成最底层的派生类保存两份最上层类的数据成员,从而造成数据冗余和内容浪费,采用虚继承。virtual可以用来修饰类中的成员函数,也可以修饰继承方式
class A
{
public:
	//int a;
    double arr[5];

	
	
};


class B:  virtual public A
{
public:
	int b;

	
	
};


class C :  virtual public A
{
public:
	int c;

	
	
};


class D: public B,  public C
{
//public:
//	int d;

};


int main() {

	D dd;
	cout<<sizeof(dd);//通过虚继承 可以让最底层类 只保留一份最上层类的数据成员,但是我们也付出了代码,也要维护指针占用的空间。

	return 0;
}
相关推荐
李少兄5 分钟前
Java 中只有值传递吗?
java·开发语言·python
tdtsmt16 分钟前
2026年SMT贴片加工选型指南:天地通电子推荐参考
c++
一木 之林25 分钟前
插件、MCP、Skill 的区别?
java·c++·人工智能
可乐鸡翅yeah_29 分钟前
hls.js 播放质量埋点实战,采集卡顿、起播、错误指标定位线上用户问题
开发语言·前端·javascript·ecmascript·音视频·m3u8·音视频在线播放
szarron1 小时前
RF Demo Kit|NanoVNA 射频演示测试板完整上手教程,滤波器、衰减器、SOLT 校准学习板
开发语言·人工智能·学习·php·射频工程·频谱仪
边境悍匪1 小时前
蜗牛学苑 Java 智能体学习 Day39|SpringAI 会话存储、Function‑Call 工具调用、MCP 思维导图复盘
java·开发语言·spring boot·学习·阿里云
ShineWinsu1 小时前
对于MySQL:内置函数的解析
linux·数据库·c++·mysql·面试·函数·查询
万物智能信息科技1 小时前
RK3568 的多路显示移植—【万物智能之开源鸿蒙OpenHarmony系统实战开发系列教程】
linux·开发语言·华为·开源·harmonyos
蓝悦无人机1 小时前
Qt Design Studio(QDS)4.8.2项目文件结构详解
开发语言·qt·qt creator·qds·项目文件结构·qtc
yxlalm2 小时前
4.java秒杀项目第四课-后端商品后台接口
java·开发语言