C#-面向对象的三大特性——多态(虚方法与重写、抽象类、接口)

多态

同一操作作用于不同的对象,可以有不同的解释,产生不同的执行结果。在运行时,可以通过指向基类的指针,来调用实现派生类中的方法。

编译时的多态性:编译时的多态性是通过重载来实现的。对于非虚的成员来说,系统在编译时,根据传递的参数、返回的类型等信息决定实现何种操作。 

运行时的多态性:运行时的多态性就是指直到系统运行时,才根据实际情况决定实现何种操作。C#中,运行时的多态性通过虚成员实现。 

编译时的多态性为我们提供了运行速度快的特点,而运行时的多态性则带来了高度灵活和抽象的特点。

   实现多态:

    1. 接口多态性。
    2. 继承多态性。
    3. 通过抽象类实现的多态性。

  override关键字:

   重写父类中的virtual修饰的方法,实现多态。

=====================================================================================================

虚方法与重写

父类中的方法在子类中并不适用,那么子类需要自主更改继承的方法或者是属性,父类中加了virtual关键字的方法才可以被子类重写,子类重写父类的方法使用的是override关键字

定义关键字:虚方法 virtual    重写 override

当实例方法声明包含 virtual 修饰符时,称该方法为虚拟方法。不存在 virtual 修饰符时,称该方法为非虚拟方法。

对于非虚的方法,无论被其所在类的实例调用,还是被这个类的派生类的实例调用,方法的执行方式不变。而对于 虚方法,它的执行方式可以被派生类改变 ,这种改变是通过方法的 重载 来实现的。

1、新建一个父类Fly,新建一个子类Bird,继承Fly,主函数中调用——

 2、新建一个子类Plane,调用父类方法——

3、鸟和飞机都会飞,但是飞机不会拍翅膀;又比如儿子继承父亲的自行车,但是继承的自行车座位比较高,不适合自己,需要进行改造,此时怎么办?——虚方法与重写

=====================================================================================================

抽象类

抽象类的创建是用来作为父类的,无法进行实例化,只能被继承;抽象方法只能在抽象类中,但是抽象类中不一定只有抽象方法,也可以有普通方法。

定义关键字: abstract 

抽象类具有以下特性:
  • 抽象类不能实例化。
  • 抽象类可以包含抽象方法和抽象访问器。
  • 不能用 sealed 修饰符修饰抽象类,因为这两个修饰符的含义是相反的。 采用 sealed 修饰符的类无法继承,而 abstract 修饰符要求对类进行继承。
  • 从抽象类派生的非抽象类必须包括继承的所有抽象方法和抽象访问器的实际实现。

1、在父类中用 abstract 修饰类,将类改为抽象类, 将某个方法用 abstract 修饰为抽象方法,此时方法没有函数体

2、在子类中继承父类,用 override 重写抽象方法

3、在主函数中调用

例如:

父类:

子类:

主函数调用:

=====================================================================================================

接口

接口是实现子类继承多个父类方法,如果父类是子类的亲爹,那么接口就是子类的干爹,子类只可以有一个亲爹即父类,但可以有多个干爹即接口。

C#接口作用的深入理解  http://blog.jobbole.com/85751/

1. 接口是一个引用类型,通过接口可以实现多重继承。
2. C#中接口的成员不能有new、public、protected、internal、private等修饰符。
3. 接口中只能声明"抽象"成员(所以不能直接下一步对接口进行实例化(即不能使用new操作符声明一个接口的实例对象)),而不能声明共有的域或者私有的成员变量。
4. 接口声明不包括数据成员,只能包含方法、属性、事件、索引等成员。
5. 接口名称一般都以“I”作为首字母(当然不这样声明也可以),这也是接口和类的一个区别之一。[2] 
6. 接口成员的访问级别是默认的(默认为public),所以在声明时不能再为接口成员指定任何访问修饰符,否则 编译器会报错。
7. 接口成员不能有static、abstract、override、virtual修饰符,使用new修饰符不会报错,但会给出警告说不需要关键字new。
8. 在声明接口成员的时候,不准为接口成员编写具体的可执行代码,也就是说,只要在对接口进行声明时指明接口的成员名称和参数就可以了。
9. 接口一旦被实现,实现类必须实现接口中的所有成员,除非实现类本身是抽象类(通过具体的可执行代码实现接口抽象成员的操作)。
 
例如:
一个完整的人由三个类组成,基础类(吃饭、睡觉)、赚钱接口(技能、地点)、娱乐接口(娱乐1、娱乐2)
要将三个类整合为一个整体,就用到了接口 
1、新建一个为抽象类的基础类作为父类

2、新建两个接口赚钱接口和娱乐接口

3、新建一个类 Man 继承其他类,并设置方法,根据需要再新建其他类继承填写信息

 

 

原文地址:https://www.cnblogs.com/qq450867541/p/6108935.html