[你必须知道的.NET]第十七回:貌合神离:覆写和重载

本文将介绍以下内容:

  • 什么是覆写,什么是重载
  • 覆写与重载的区别
  • 覆写与重载在多态特性中的应用

 

 

 

 

1. 引言

覆写(override)与重载(overload),是成就.NET面向对象多态特性的基本技术之一,两个貌似相似而实则不然的概念,常常带给我们很多的误解,因此有必要以专题来讨论清楚其区别,而更重要的是关注其在多态中的应用。

在系列中,我们先后都有关于这一话题的点滴论述,本文以专题的形式再次做以深度讨论,相关的内容请对前文做以参考。  

2. 认识覆写和重载

从一个示例开始来认识什么是覆写,什么是重载?

    abstract class  Base
    {
        
//定义虚方法
        public virtual void MyFunc()
        { 
        }

        
//参数列表不同,virtual不足以区分
        public virtual void MyFunc(string str)
        {
        }

        
//参数列表不同,返回值不同
        public bool MyFunc(string str, int id)
        {
            Console.WriteLine(
"AAA");
            
return true;
        }

        
//参数列表不同表现为个数不同,或者相同位置的参数类型不同 
        public bool MyFunc(int id, string str)
        {
            Console.WriteLine(
"BBB");
            
return false;
        }

        
//泛型重载,允许参数列表相同
        public bool MyFunc<T>(string str, int id)
        {
            
return true;
        }

        
//定义抽象方法
        public abstract void Func();
    }

    
class Derived: Base
    {
        
//阻隔父类成员
        public new void MyFunc()
        {
        }

        
//覆写基类成员
        public override void MyFunc(string str)
        {
            
//在子类中访问父类成员
            base.MyFunc(str);
        }

        
//覆写基类抽象方法
        public override void Func()
        {
            
//实现覆写方法
        }
}


2.1 覆写基础篇

覆写,又称重写,就是在子类中重复定义父类方法,提供不同实现,存在于有继承关系的父子关系。当子类重写父类的虚函数后,父类对象就可以根据根据赋予它的不同子类指针动态的调用子类的方法。从示例的分析,总结覆写的基本特征包括:

  • 在.NET中只有以virtual和abstract标记的虚方法和抽象方法才能被直接覆写。
  • 覆写以关键字override标记,强调继承关系中对基类方法的重写。
  • 覆写方法要求具有相同的方法签名,包括:相同的方法名、相同的参数列表和相同的返回值类型。
概念:虚方法 

虚方法就是以virtual关键字修饰并在一个或多个派生类中实现的方法,子类重写的虚方法则以override关键字标记。虚方法调用,是在运行时确定根据其调用对象的类型来确定调用适当的覆写方法。.NET默认是非虚方法,如果一个方法被virtual标记,则不可再被static、abstrcat和override修饰。 

概念:抽象方法 

抽象方法就是以abstract关键字修饰的方法,抽象方法可以看作是没有实现体的虚方法,并且必须在派生类中被覆写,如果一个类包括抽象方法,则该类就是一个抽象类。因此,抽象方法其实隐含为虚方法,只是在声明和调用语法上有所不同。abstract和virtual一起使用是错误的。

2.2 重载基础篇

重载,就是在同一个类中存在多个同名的方法,而这些方法的参数列表和返回值类型不同。值得注意的是,重载的概念并非面向对象编程的范畴,从编译器角度理解,不同的参数列表、不同的返回值类型,就意味着不同的方法名。也就是说,方法的地址,在编译期就已经确定,是这一种静态绑定。从示例中,我们总结重载的基本特征包括:

  • 重载存在于同一个类中。
  • 重载方法要求具有相同的方法名,不同的参数列表,返回值类型可以相同也可以不同(通过operator implicit 可以实现一定程度的返回值重载,不过不值得推荐)。
  • .NET 2.0引入泛型技术,使得相同的参数列表、相同的返回值类型的情况也可以构成重载。  

3. 在多态中的应用

多态性,简单的说就是“一个接口,多个方法”,具体表现为相同的方法签名代表不同的方法实现,同一操作作用于不同的对象,产生不同的执行结果。在.NET中,覆写实现了运行时的多态性,而重载实现了编译时的多态性。

运行时的多态性,又称为动态联编,通过虚方法的动态调度,在运行时根据实际的调用实例类型决定调用的方法实现,从而产生不同的执行结果。

    class  Base
    {
        
public virtual void MyFunc(string str)
        {
            Console.WriteLine(
"{0} in Base", str);
        }
    }

    
class Derived: Base
    {
        
//覆写基类成员
        public override void MyFunc(string str)
        {
            Console.WriteLine(
"{0} in Derived", str);
        }

        
public static void Main()
        {
            Base B 
= new Base();
            B.MyFunc(
"Hello");
            Derived A 
= new Derived();
            B 
= A;
            B.MyFunc(
"Morning");
        }
    }

从结果中可知,对象B两次执行B.MyFunc调用了不同的方法,第一次调用基类方法MyFunc,而第二次调用了派生类方法MyFunc。在执行过程中,对象B先后指向了不同的类的实例,从而动态调用了不同的实例方法,显然这一执行操作并非确定于编译时,而是在运行时根据对象B执行的不同类型来确定的。我们在此不分析虚拟方法的动态调度机制,而只关注通过虚方法覆写而实现的多态特性,详细的实现机制请参考本系列的其它内容。

编译时的多态性,又称为静态联编,一般包括方法重载和运算符重载。对于非虚方法来说,在编译时通过方法的参数列表和返回值类型决定不同操作,实现编译时的多态性。例如,在实际的开发过程中,.NET开发工具Visual Studio的智能感知功能就很好的为方法重载提供了很好的交互手段,例如:

从智能感知中可知方法MyFunc在派生类Derived中有三次重载,调用哪种方法由程序开发者根据其参数、返回值的不同而决定。由此可见,方法重载是一种编译时的多态,对象A调用哪种方法在编译时就已经确定。

4. 比较,还是规则

  • 如果基访问引用的是一个抽象方法,则将导致编译错误。
    abstract class  Base
    {
        
public abstract void Func();
    }

    
class Derived: Base
    {
        
//覆写基类抽象方法
        public override void Func()
        {
            
base.Func();
        }
    }
  • 虚方法不能是静态的、密封的。
  • 覆写实现的多态确定于运行时,因此更加的灵活和抽象;重载实现的多态确定于编译时,因此更加的简单和高效。二者各有特点与应用,不可替代。

在下表中,将覆写与重载做以总结性的对比,主要包括:

 

规则

覆写(override

重载(overload

存在位置

存在于有继承关系的不同类中

存在于同一个类中

调用机制

运行时确定

编译时确定

方法名

必须相同

必须相同

参数列表

必须相同

必须不同

返回值类型

必须相同

可以不相同

泛型方法

可以覆写

可以重载


注:参数列表相同表示参数的个数相同,并且相同位置的参数类型也相同。

5. 结论

深入的理解覆写和重载,是对多态特性和面向对象机制的有力补充,本文从基本概念到应用领域将两个概念进行一一梳理,通过对比整理区别,还覆写和重载以更全面的认知角度,同时也更能从侧面深入的了解运行时多态与编译时多态的不同情况。

 

 

参考文献

 

(web)TerryLee, 再谈重载与覆写,http://www.cnblogs.com/Terrylee/archive/2006/03/10/347104.html

(web)失落的BLOGS,C#泛型,http://www.cnblogs.com/lianyonglove/archive/2007/07/27/720682.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/438735.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

鸿蒙系统正式开源,余承东:鸿蒙系统正式开源,友商也可以使用!

鸿蒙OS2.0正式开源&#xff1a;从PPT走向前台&#xff0c;该谁脸红了&#xff1f;在9月10日的开发者大会上&#xff0c;华为鸿蒙2.0发布&#xff0c;已经不再是某些人嘴中的PPT、又哄又蒙的鸿蒙了。说鸿蒙是PPT的言论&#xff0c;在前不久还能看到&#xff0c;如今鸿蒙已经发布…

[你必须知道的.NET]第十八回:对象创建始末(上)

本文将介绍以下内容&#xff1a; 对象的创建过程内存分配分析内存布局研究1. 引言 了解.NET的内存管理机制&#xff0c;首先应该从内存分配开始&#xff0c;也就是对象的创建环节。对象的创建&#xff0c;是个复杂的过程&#xff0c;主要包括内存分配和初始化两个环节。例如&…

[你必须知道的.NET]第十九回:对象创建始末(下)

本文将介绍以下内容&#xff1a; 对象的创建过程内存分配分析内存布局研究接上回[第十八回&#xff1a;对象创建始末&#xff08;上&#xff09;]&#xff0c;继续对对象创建话题的讨论>>> 2.2 托管堆的内存分配机制 引用类型的实例分配于托管堆上&#xff0c;而线…

android material 颜色值,Android Material Colors 谷歌 Material Design 标准颜色

Android Material Colors谷歌 Material Design 标准颜色。调色板资源文件通过 doc-getter 自动抓取生成。运行 Demo 来查看效果。UsageGradlecompile com.takwolf.android.materialdesign:color:0.0.1Stylecolor/material_indigo_500color/material_indigo_700color/material_p…

突然吐字不清_要注意说话吐字不清小心是脑中风前兆

任何疾病发病之前往往会有一些前兆出现&#xff0c;像是脑中风这种疾病在发作之前也是有前兆的&#xff0c;若是朋友们能够尽早的发现就能够在发病前进行治疗了。朋友们要注意的是说话吐字不清小心是脑中风前兆&#xff0c;这是脑中风发病前的典型前兆&#xff0c;还有头晕、呕…

c++ vs release没有exe_未来安全 | 第一次Geant4培训总结 | 有没有你关注的问题呢?...

Geant4简介Geant4是蒙卡工具包&#xff0c;模拟很多粒子&#xff0c;记录一些统计量&#xff0c;用这些统计量去估计真实的物理实验的结果。蒙卡模拟程序&#xff0c;从最老的MCNP&#xff0c;到PENELOPE&#xff0c;FLUKA等。MCNP是用输入卡片(输入文件)实现的&#xff0c;在一…

[你必须知道的.NET]第二十一回:认识全面的null

说在&#xff0c;开篇之前 null、nullable、??运算符、null object模式&#xff0c;这些闪亮的概念在你眼前晃动&#xff0c;我们有理由相信“存在即合理”&#xff0c;事实上&#xff0c;null不光合理&#xff0c;而且重要。本文&#xff0c;从null的基本认知开始&#xff0…

html用表格做个人主页页面,利用HTML的表格进行页面布局

在DIVCSS布局出现前&#xff0c;基本上所用的网站都使用table来进行布局。因为table布局很简单&#xff0c;但是table布局不灵活且代码很多。下面将介绍怎样使用table来进行布局。实例&#xff1a;我们来布局一个常见网站后台程序的架构。布局图如下所示&#xff1a;实例代码&a…

cesium坡度坡向分析_景观设计分析图制作技巧到底是什么?

国外设计中&#xff0c;人们都开始用动态分析图啦厉害的不要不要啊&#xff01;如果你也想做如此高逼格的分析图记得往下看&#xff01;景观设计分析为&#xff1a;人文&#xff0c;背景&#xff0c;区位&#xff0c;现状&#xff0c;历史&#xff0c;功能&#xff0c;流线&…

采购模板html5,蓝色的采购信息管理系统手机界面wap模板

手机版大气信息管理系统界面模板&#xff0c;采购信息管理wap手机模板下载。资源下载此资源下载价格为4D币&#xff0c;请先登录资源文件列表codedown123-080801-25/business_log.html , 6657codedown123-080801-25/choose.html , 6869codedown123-080801-25/css/animate.css ,…

adobe audition cs6 能打开mpcm文件吗?_Adobe全家桶出现这些漏洞,赶紧上官网下载补丁吧...

导语&#xff1a;Adobe已发布了计划的2020年7月安全更新&#xff0c;涵盖了五个不同产品领域的缺陷&#xff1a;Creative Cloud Desktop&#xff1b;媒体编码器&#xff1b;下载管理器; 真正的服务&#xff1b;和ColdFusion。其中四个错误的严重性被评为严重&#xff0c;而其他…

详解CSS的相对定位和绝对定位

CSS的相对定位和绝对定位 一、Static 静态定位 通常情况下&#xff0c;我们元素的position属性的值默认为static 就是没有定位&#xff0c;元素出现在正常的文档流中&#xff0c;这个时候你给这个元素设置的left,right,bottom,top这些偏移属性都是没有效果的&#xff0c;不会生…

观看实验中微型计算机虚拟拆装演示,虚拟仿真实验 北斗一号微机原理虚拟仿真实验系统64位 v3.0...

下面我们对虚拟仿真实验 北斗一号微机原理虚拟仿真实验系统64位 v3.0文件阐述相关使用资料和虚拟仿真实验 北斗一号微机原理虚拟仿真实验系统64位 v3.0文件的更新信息。虚拟仿真实验 北斗一号微机原理虚拟仿真实验系统64位 v3.0“微机原理虚拟仿真实验”适用于《微机原理》《微…

[你必须知道的.NET]第二十二回:字符串驻留(上)---带着问题思考

走钢丝的人&#xff0c;在刺激中体验快感。带着问题思考&#xff0c;在问题上迸发火花。 或者给问题以答案&#xff0c;或者给答案以问题&#xff0c;你可能永远无法看清全部&#xff0c;但是总能从一点突破很多。事实的关键就在于面对问题&#xff0c;我该如何思考&#xff1…

springboot超详细教程_超详细便当袋教程 || 特殊时期,自己带饭最安心!

持续受疫情影响&#xff0c;闷在家里的广大网友们早就坐不住了。尤其是最近各地复工陆续开始&#xff0c;小心心是不是开始躁动了&#xff1f;终于可以出门放飞自我&#xff0c;放肆吃吃喝喝了嘛&#xff1f;再忍一忍呀同志们&#xff01;疫情还没结束&#xff0c;病毒还没被消…

[你必须知道的.NET]第二十三回:品味细节,深入.NET的类型构造器

1 引言今天Artech兄在《关于Type Initializer和 BeforeFieldInit的问题&#xff0c;看看大家能否给出正确的解释》一文中让我们认识了一个关于类型构造器调用执行的有趣示例&#xff0c;其中也相应提出了一些关于beforefieldinit对于类型构造器调用时机的探讨&#xff0c;对于我…

[你必须知道的.NET]第二十四回:认识元数据和IL(上)

说在&#xff0c;开篇之前很早就有说说Metadata&#xff08;元数据&#xff09;和IL&#xff08;中间语言&#xff09;的想法了&#xff0c;一直在这篇开始才算脚踏实地的对这两个阶级兄弟投去些细关怀&#xff0c;虽然来得没有《第一回&#xff1a;恩怨情仇&#xff1a;is和as…

计算机无法找到组件c0000135,电脑显示没有找到dwmapi.dll组件怎么办?计算机丢失dwmapi.dll的处理方法...

很多用户在操作Windows系统的过程中发现“没有找到dwmapi.dll”&#xff0c;如果丢失dwmapi.dll组件会导致应用程序无法运行。其实&#xff0c;大家可以尝试在相关网站下载所缺少的组件&#xff0c;或者是通过第三方软件来进行安装下载&#xff0c;这里小编带领大家看看具体解决…

[你必须知道的.NET]第二十五回:认识元数据和IL(中)

说在&#xff0c;开篇之前书接上回[第二十四回&#xff1a;认识元数据和IL&#xff08;上&#xff09;]&#xff0c;我们对PE文件、程序集、托管模块&#xff0c;这些概念与元数据、IL的关系进行了必要的铺垫&#xff0c;同时顺便熟悉了以ILDASM工具进行反编译的基本方法认知&a…

小学计算机制作表格教案,小学信息技术《表格的制作》教案

小学信息技术《表格的制作》教案教学目标&#xff1a;知识目标&#xff1a;了解什么是网页表格能力目标&#xff1a;学会插入表格&#xff1b;掌握在表格中插入文字和图片的方法&#xff1b;学会设置单元格属性&#xff1b;掌握拆分和合并单元格。情感目标&#xff1a;通过研究…