C语言实现C++继承和多态的代码分享

 更新时间:2020年4月25日 17:30  点击:2195

这个问题主要考察的是C和C++的区别,以及C++中继承和多态的概念。

C和C++的区别

C语言是面向过程的语言,而C++是面向对象的过程。

什么是面向对象和面向过程?

面向过程就是分析解决问题的步骤,然后用函数把这些步骤一步一步的进行实现,在使用的时候进行一一调用就行了,注重的是对于过程的分析。面向对象则是把构成问题的事进行分成各个对象,建立对象的目的也不仅仅是完成这一个个步骤,而是描述各个问题在解决的过程中所发生的行为。

面向对象和面向过程的区别?

面向过程的设计方法采用函数来描述数据的操作,但将函数与操作的数据进行分离开来。

面向对象的设计方法是将对象和数据进行封装起来成为一个整体。

面向过程以设计步骤为过程,后期难以维护。

面向对象设计以数据为中心,数据相对与功能来说具有较强的稳定性更加易于维护。

面向对象的三大特征

封装

对于封装来说就是数据与具体操作实现的代码都放在某个对象的内部,使这些代码的具体细节不被外界发现,只留下一些接口供外部来使用,而不能一任何的形式来对象内部的实现。使用封装能够隐藏具体的实现的细节,使代码更加易于维护并且保证了系统的安全性。

继承

继承机制是面向对象程序设计使代码进行复用的最重要的手段,他允许程序员在保证类原有类特性的基础上进行扩展来增加功能。这样新产生的类就被称为派生类,继承就可以表现面向对象机制的的层次结构。

多态

多态简单点说就是“一个接口,多种实现”,就是同一种事物表现出的多种形态。多态在面向对象语言中是指:接口多种的不同实现方式。也就是复用相同接口,实现不同操作。

C++多态支持两种多态性,编译时多态和运行时多态。 编译时多态是通过重载函数来实现的,运行时多态是通过虚函数来实现的。 静态多态:编译器在编译期间完成,编译器根据函数实参的类型(可能会隐式类型转换),可推断出要调用哪个函数,如果有对应的函数就调用相应的函数,否则就报一个编译错误。动态多态:在函数执行期间(非编译期)判断所引用对象的实际类型,根据实际类型的调用相应的方法。使用virtual关键字修饰类的成员函数,指明该函数为虚函数,派生类需要重新实现,编译器将实现动态绑定。

动态多态实现的条件: 1>、使用场景:父类的指针或者引用指向父类或者子类的对象(由赋值兼容规则决定); 2>、实现多态的两个条件:虚函数的重写;父类的指针或者引用调用重写的虚函数。 3>、若父类中的成员函数加上virtual关键字,则子类中重写的该函数默认virtual,可以不指定,但是一般加上; 重写:子类重写父类的虚函数,要求函数名称,函数参数,返回值完全一样(协变除外);

总的来说:封装可以隐藏实现细节包括包含私有成员,使得代码模块增加安全指数;继承可以扩展已存在的模块,为了增加代码的复用性;多态则是为了保证类在继承和派生的时候,类的实例被正确调用,实现了接口的重用

C模拟实现多态

C++中的多态

我们知道的是在C++中会维护一张虚函数表,根据赋值兼容规则,我们知道父类的指针或者引用是可以指向子类对象的。如果一个父类的指针或者引用调用父类的虚函数则该父类的指针会在自己的虚函数表中查找自己的函数地址,如果该父类对象的指针或者引用指向的是子类的对象,而且该子类已经重写了父类的虚函数,则该指针会调用子类的已经重写的虚函数。
//c++中的多态

class A
{
public:
  virtual void fun()//虚函数实现
  {
    cout << "Base A::fun() " << endl;
  }
};

class B:public A
{
public:
  virtual void fun()//虚函数实现,子类中virtual关键字可以没有
  {
    cout << "Derived B::fun() " << endl;
  }
};

void Test1()
{
  A a;//基类对象
  B b;//派生类对象

  A* pa = &a;//父类指针指向父类对象
  pa->fun();//调用父类的函数

  pa = &b; //父类指针指向子类对象,多态实现
  pa->fun();//调用派生类同名函数
}

C语言实现多态

我们知道在C语言中是没有class类这个概念的,但是有struct结构体,我们可以考虑使用struct来模拟;但是在C语言的结构体内部是没有成员函数的,如果实现这个父结构体和子结构体共有的函数呢?我们可以考虑使用函数指针来模拟。但是这样处理存在一个缺陷就是:父子各自的函数指针之间指向的不是类似C++中维护的虚函数表而是一块物理内存,如果模拟的函数过多的话就会不容易维护了。

//C实现动态,用到函数指针

typedef void(*FUN)();//重定义一个函数指针类型

//父类
struct Base 
{
  FUN _f;
};

//子类
struct Derived
{
  Base _b;//在子类中定义一个基类的对象即可实现对父类的继承
};


void FunB()
{
  printf("%s\n", "Base::fun()");
}
void FunD()
{
  printf("%s\n", "Derived::fun()");
}

void Test2()
{
  Base b;//父类对象
  Derived d;//子类对象

  b._f = FunB;//父类对象调用父类同名函数
  d._b._f = FunD;//子类调用子类的同名函数

  Base *pb = &b;//父类指针指向父类对象
  pb->_f();

  pb = (Base *)&d;//让父类指针指向子类的对象,由于类型不匹配所以要进行强转
  pb->_f();

}

[!--infotagslink--]

相关文章

  • 深入分析c# 继承

    这篇文章主要介绍了c# 继承的相关资料,文中讲解的非常细致,代码帮助大家更好的理解和学习,感兴趣的朋友可以了解下...2020-11-03
  • php构造方法中析构方法在继承中的表现

    这篇文章主要为大家详细介绍了php构造方法中析构方法在继承中的表现,感兴趣的小伙伴们可以参考一下...2016-04-15
  • javascript中的3种继承实现方法

    这篇文章主要介绍了javascript中的3种继承实现方法,包括使用Object.create实现类式继承、使用utilities工具包自带的util.inherites、使用extends关键字,非常的实用,希望对大家了解javascript继承能够有所帮助...2016-01-30
  • C#使用虚拟方法实现多态

    这篇文章主要介绍了C#使用虚拟方法实现多态,涉及C#多态的实现技巧,具有一定参考借鉴价值,需要的朋友可以参考下...2020-06-25
  • 原生Javascript实现继承方式及其优缺点详解

    JS作为面向对象的弱类型语言,继承也是其非常强大的特性之一,那么这篇文章主要给大家介绍了关于原生Javascript实现继承方式及其优缺点的相关资料,需要的朋友可以参考下...2021-07-21
  • 理解js对象继承的N种模式

    这篇文章主要为大家举例介绍了js对象继承的几种模式,内容很全面,感兴趣的小伙伴们可以参考一下...2016-01-26
  • js继承的6种方式详解

    这篇文章主要给大家介绍了关于js继承的6种方式,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧...2021-04-06
  • 简单理解JavaScript中的封装与继承特性

    这篇文章主要介绍了JavaScript中的封装与继承特性,封装与继承是基于对象编程概念中的基本特性,需要的朋友可以参考下...2016-03-22
  • Spring Cloud中使用Feign,@RequestBody无法继承的解决方案

    这篇文章主要介绍了Spring Cloud中使用Feign,@RequestBody无法继承的解决方案,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教...2021-10-22
  • ES6新特性之类(Class)和继承(Extends)相关概念与用法分析

    这篇文章主要介绍了ES6新特性之类(Class)和继承(Extends)相关概念与用法,结合实例形式较为详细的分析了ES6中类(Class)和继承(Extends)的基本概念、语法、使用方法与注意事项,需要的朋友可以参考下...2017-05-27
  • js中实现继承的五种方法

    这篇文章主要介绍了js中实现继承的五种方法,帮助大家更好的理解和使用JavaScript,感兴趣的朋友可以了解下...2021-01-26
  • 浅谈C# 类的继承

    本文主要介绍了C# 类的继承相关知识。具有很好的参考价值,下面跟着小编一起来看下吧...2020-06-25
  • C++设计类不能被继承的方法实例讲解

    在Java 中定义了关键字final,被final修饰的类不能被继承,C++中如何实现,下面我们来看一个例子...2020-04-25
  • C#中实现多继承的方法

    这篇文章主要介绍了C#中实现多继承的方法,本文通过给接口添加扩展的方法实现了C#的多继承,需要的朋友可以参考下...2020-06-25
  • 谈一谈javascript中继承的多种方式

    本文就和大家谈一谈javascript中的继承,什么是继承,继承的作用,以及js继承的实现代码,感兴趣的小伙伴们可以参考一下...2016-02-21
  • 理解javascript对象继承

    这篇文章主要帮助大家理解javascript对象继承,先从一个问题出发,引入javascript对象继承相关知识,感兴趣的小伙伴们可以参考一下...2016-04-19
  • Java编程 多态

    这篇文章主要介绍了关于Java编程的多态,多态通过分离做什么和怎么做,从另一个角度将接口和实现分离开来。构建可扩展的程序,需要的朋友可以参考下...2021-10-08
  • php 三大特点:封装,继承,多态

    小编给大家推荐的这篇文章介绍了php 三大特点:封装,继承,多态,非常实用,有兴趣的同学快看看吧。 一.封装目的:让类更安全做法:成员变量变为私有的,通过方法间接操作成员变...2017-07-06
  • C#中面向对象编程机制之继承学习笔记

    这篇文章主要介绍了C#中面向对象编程机制之继承学习笔记,本文给出一个简单子实例讲解C#中的继承,并讲解了一些C#继承的知识技巧,需要的朋友可以参考下...2020-06-25
  • C++ 中继承与动态内存分配的详解

    这篇文章主要介绍了C++ 中继承与动态内存分配的详解的相关资料,这里提供实例帮助大家学习理解这部分内容,需要的朋友可以参考下...2020-04-25