C#中的扩展方法

扩展方法使你能够向现有类型“添加”方法,而无需创建新的派生类型、重新编译或以其他方式修改原始类型。 扩展方法是一种特殊的静态方法,但可以像扩展类型上的实例方法一样进行调用。 以上是msdn官网对扩展方法的描述,现在我通过一个情景例子来对此进行阐释。假设一个控制台程序class
Program{}里面的主函数如下:

static void Main(string[] args)
{
DateTime now = DateTime.Now;
string time = now.ToString("yyyy-MM-dd HH:mm:ss");
Console.WriteLine(time);
Console.ReadKey();
}

假设需求变了,日期的显示格式要变成"yyyy-MM-dd"这种格式,当然只需要初始化time时按下面写法改写即可:

string time = now.ToString("yyyy-MM-dd");

但是如果要改变日期格式的有很多个类呢?每个都要改一次吗?这样一旦需求变来变去就忙死人了。传统的解决方式是封装一个帮助类,在里面写方法,然后供其他类调用。

本例在当前项目模仿添加一个DateHelper类:public
class DateHelper{},在类里面定义方法:

public static string DateToString(DateTime dt)
{
return dt.ToString("yyyy-MM-dd HH:mm:ss");
}

于是原来的主函数改写如下:

static void Main(string[] args)
{
DateTime now = DateTime.Now;
string time = DateHelper.DateToString(now);
Console.WriteLine(time);
Console.ReadKey();
}

此时如果变需求,只需要改写DateHelp类里的DateToString()方法就行了,不管有多少个类调用此方法,都会被影响。问题解决了,可是这样要调用另一个类的方法,还是有点麻烦,有没有什么方法能够让我们像now.DateToString()一样直接调用呢?当然DateTime是微软写好的,我们改不了,无法创建想要的实例方法,于是,便引出了扩展方法。
下面是扩展方法的要素:

1.此方法必须是一个静态方法

2.此方法必须放在静态类中

3.此方法的第一个参数必须以this开头,并且指定此方法是扩展自哪个类型

根据以上要素,我们DateHelper类改成静态类:public static class DateHelper{} ,同时改写DateToString()方法:

public static string DateToString(this DateTime dt)
{
return dt.ToString("yyyy-MM-dd HH:mm:ss");
}

此时回到主函数方法体,输入"now."便可以看见自动提示有个DateToString()方法,于是代码可以这样写:

static void Main(string[] args)
{
DateTime now = DateTime.Now;
string time = now.DateToString();
Console.WriteLine(time);
Console.ReadKey();
}

显而易见,这样用起来会更加便捷,而且这样让我们看起来确实就像是被扩展类型本身具有的实例方法一样,可读性很高。下面概括一下扩展方法的特点:

1.扩展方法扩展自哪个类型,就必须是此类型的变量来使用,其他类型无法使用,本例扩展自DateTime类型,就只能是被DateTime类型的变量.出来(now.DateToString())

2.扩展方法中的this后面的参数不属于方法的参数,本例是无参数,this后面的DateTime dt是指明扩展方法扩展自何种类型

3.如果扩展方法和实例方法具有相同的签名,则优先调用实例方法

4.扩展自父类上的方法,可以被子类的对象直接使用

5.扩展自接口上的方法,可以被实现类的对象直接使用

6.扩展方法最终还是被编译器编译成:静态类.静态方法(),本例中now.DateToString()最终还是会被编译成DateHelper.DateToString(now),这是它的本质

实际上,我们可能会遇到这样的情景,如在接口扩展一个方法的时候,所有的原本已实现该接口的类都要实现新扩展的方法,这样的改动是一个很麻烦的工作,可以使用扩展方法“曲线救国”;而有时候我们想为某个类添加新方法却不想改动这个类,那么扩展方法这种“伪添加”方法的方式就体现出它的价值了。最常见的扩展方法是LINQ标准查询运算符,运用广泛,这种方便快捷的方式理应博得码农们点1024个赞。

不逆袭,不 I T !

Can't fly , can't be an IT guy !
转载自:http://www.cnblogs.com/0weibin/p/3954639.html

C#中的扩展方法(向已有类添加方法,但无需创建新的派生类型)的更多相关文章

  1. Groovy中如何向已有的类添加新方法

    Groovy 中有多种途径实现向原有类添加方法,具体有如下几种: MOP(meta object protocol) -- 详见 ExpandoMetaClass 扩展方法 -- GDK采用的此方法 ...

  2. 运行过程中给类添加方法 types.MethodType

    class Person(object): def __init__(self,name = None,age = None): self.name = name#类中拥有的属性 self.age = ...

  3. runtime-给系统已有类添加属性

    在没有接触runtime之前,我们接触到的能给类进行扩展的方法有类目(category)和延展(extension)两种.类目(category)可以给系统已有类添加扩展方法但是不能添加属性,并且被添 ...

  4. Javascript中两种最通用的定义类的方法

    在Javascript中,一切都是对象,包括函数.在Javascript中并没有真正的类,不能像C#,PHP等语言中用 class xxx来定义.但Javascript中提供了一种折中的方案:把对象定 ...

  5. 构造方法概念,自定义构造(init)方法的用途, 类工厂方法(就是直接用类名 类调用)

    一. 构造方法 构造方法:在OC中init开头的方法, 我们称之为构造方法 构造方法的用途: 用于初始化一个对象, 让某个对象一创建出来就拥有某些属性和值 // 比如我们定义一个Person的类,然后 ...

  6. .NET C#利用反射获取类文件以及其中的方法&属性 并获取类及方法上的特性

    了解C#特性类并声明我们自己的特性类[AttributeTest]代码如下 using System; namespace AttributeTest { /* 特性说明 特性本质是一个继承和使用了系 ...

  7. python3 高级编程(二) 动态给类添加方法功能

    class Student(object): pass 给实例绑定一个属性: >>> s = Student() >>> s.name = 'Michael' # ...

  8. [ActionScript3.0] 为内建类添加方法

    通过使用prototype在继承内建类特性的同时加入新方法 Array.prototype.removeElement = function (item:*):void { var index:int ...

  9. 已有使用Key登陆机器,创建新账号并使用新Key登陆

    背景信息:CentOS6.9机器,目前是使用Key进行登陆的,现在需要创建一个新账号并使用新生成的Key进行登陆使用 使用连接Linux工具:XShell 1.在当前机器中创建一个新用户: # use ...

随机推荐

  1. 常用的re模块的正则匹配的表达式

    07.01自我总结 常用的re模块的正则匹配的表达式 一.校验数字的表达式 1.数字 ^[0-9]\*$ 2.n位的数字 ^\d{n}$ 3.至少n位的数字 ^\d{n,}$ 4.m-n位的数字 ^\ ...

  2. Gin框架 - 自定义错误处理

    目录 概述 错误处理 自定义错误处理 panic 和 recover 推荐阅读 概述 很多读者在后台向我要 Gin 框架实战系列的 Demo 源码,在这里再说明一下,源码我都更新到 GitHub 上, ...

  3. JSON的简单使用之提取多层嵌套的JSON(C#)

    JSON.NET(http://json.codeplex.com/)使用来将.NET中的对象转换为JSON字符串(序列化?),或者将JSON字符串转换为.NET中已有类型的对象(反序列化?) 反序列 ...

  4. win8上安装sql server (2008 and 2008 R2)存在兼容性问题怎么解决

     安装sql2008R2之前,需要先下载"AccessDatabaseEngine"组件并安装(百度上搜索下载就可以了),打补丁重启,再安装sql2008,安装时候提示兼容性问 ...

  5. 前端jQuery学习(一)

    把最近学习的前端框架jQuery整理一下.你可能听说过jQuery,因为他是JavaScript世界中使用最广泛的一个库. 江湖传言,全世界大约有80~90%的网站直接或间接地使用了jQuery.鉴于 ...

  6. (11)ASP.NET Core 中的配置一(Configuration)

    1.前言 ASP.NET Core在应用程序上引入Microsoft.Extensions.Configuration配置,可以支持多种方式配置,包括命令行配置.环境变量配置.文件配置.内存配置,自定 ...

  7. 二、PyTorch 入门实战—Variable(转)

    目录 一.概念 二.Variable的创建和使用 三.标量求导计算图 四.矩阵求导计算图 五.Variable放到GPU上执行 六.Variable转Numpy与Numpy转Variable 七.Va ...

  8. 箭头函数=>

    箭头函数特点一:没有自己的this对象,其this对象为所在环境 特点二 :没有arguments参数 可以用...rest代替特点三:不能使用构造函数,不可使用new命令,否则会报错 //函数的扩展 ...

  9. Hexo结合github制作博客

    https://blog.csdn.net/Hoshea_chx/article/details/78826689 hexo(themes) vuePress jekylly

  10. 01-Spring Security框架学习

    目录 01-Spring Security框架学习 简介 Spring Security 是什么 Spring Security 解决那些问题 Spring Security 的优点 历史背景 Spr ...