C#扩展方法的理解

扩展方法使您能够向现有类型“添加”方法,而无需创建新的派生类型、重新编译或以其他方式修改原始类型。

这是msdn上说的,也就是你可以对String,Int,DataRow,DataTable等这些类型的基础上增加一个或多个方法,使用时不需要去修改或编译类型本身的代码。

扩展一般类型有:

1:.Net内置对象的扩展方法  就是.net框架内自带的对象进行扩展,例如 string类, List类等

2:一般对象的扩展方法 和Framework内置对象一样,自定义的对象也可以增加扩展方法。

例如:自定义一个类:public class Person{public string Name { set; get; } public int Age { set; get; }}

那么可以对这个类做扩展方法:

//Person的扩展方法,根据年龄判断是否是成年人
        public static bool GetBIsChild(this Person oPerson)
        {
            if (oPerson.Age >= 18)
                return false;
            else
                return true;
        }

3:泛型对象的扩展方法

public static class DataContractExtensions
{
  //测试方法
  public static T Test<T>(this T instance) where T : Test2
  {
       T Res = default(T);
       try
       {
           Res.AttrTest = instance.AttrTest.Substring(0,2);
           //其他复杂逻辑...


      }
      catch
      { }
      return Res;
  }

}

public class Test2
{
public string AttrTest { set; get; }
}

使用扩展方法有几个值得注意的地方:

(1)扩展方法不能和调用的方法放到同一个类中

(2)第一个参数必须要,并且必须是this,这是扩展方法的标识。如果方法里面还要传入其他参数,可以在后面追加参数

(3)扩展方法所在的类必须是静态类

(4)最好保证扩展方法和调用方法在同一个命名空间下

 

先做个例子吧,以String为例,需要在字符串类型中加一个从字符串转为数值的功能。

以往我们可能是这样做的,会专门写一个方法做过转换

 

public static int StrToInt(string s)

{

    int id;

    int.TryParse(s, out id);//这里当转换失败时返回的id为0

    return id;

}

调用就使用

 

string s = "abc";

int i = StrToInt(s);

若是String类型有一个名为ToInt()(从字符串转为数值)的方法,就可以这样调用了

 

string s = "abc";

int i = s.ToInt();

这样看起来是不是更好,下面来看看具体怎么实现吧

第一步:

我先创建一个解决方案,一个web应用程序(webtest)及一个类库(W.Common)

在webtest项目添加引用W.Common项目

第二步:在类库中新建一个名为EString.cs类

 

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

 

namespace W.Common

{

    public static class EString

    {

        /// <summary>

        /// 将字符串转换为Int

        /// </summary>

        /// <param name="t"></param>

        /// <returns>当转换失败时返回0</returns>

        public static int ToInt(this string t)

        {

            int id;

            int.TryParse(t, out id);//这里当转换失败时返回的id为0

            return id;

        }

    }

}

看了上面的代码了吧,扩展方法规定类必须是一个静态类,EString是一个静态类,里面包含的所有方法都必须是静态方法。

msdn是这样规定扩展方法的:“扩展方法被定义为静态方法,但它们是通过实例方法语法进行调用的。 它们的第一个参数指定该方法作用于哪个类型,并且该参数以 this 修饰符为前缀。

EString里有一个ToInt的静态方法,他接收一个自身参数this,类型为string,this string必须在方法参数的第一个位置。

这句话什么意思,即你需要对string扩展一个ToInt方法,this是string实例化后的对象,这可能说的不太清楚,我的表述能力能弱,不要见怪呀。。。通俗的说就是,扩展方法跟静态类的名称无关,只需要在一个静态类里面定义一个静态方法,第一个参数必须this string (string是一种类型,这里只是一个例子,也可以是其他类型)开头。

如果需要你要对DateTime类型扩展方法名为IsRange(判断是否在此时间范围内),代码如下:

 

/// <summary>

   /// 此时间是否在此范围内 -1:小于开始时间 0:在开始与结束时间范围内 1:已超出结束时间

   /// </summary>

   /// <param name="t"></param>

   /// <param name="startTime"></param>

   /// <param name="endTime"></param>

   /// <returns></returns>

   public static int IsRange(this DateTime t, DateTime startTime, DateTime endTime)

   {

       if (((startTime - t).TotalSeconds > 0))

       {

           return -1;

       }

 

       if (((endTime - t).TotalSeconds < 0))

       {

           return 1;

       }

 

       return 0;

   }

这里的扩展方法是用this DateTime打头,那么就可以这样调用

 

time.IsRange(t1,t2);//判断时间time是否在t1到t2的范围内

当前代码在使用扩展方法前需要先引用命名空间

 

using System;

using System.Collections.Generic;

using System.Linq;

using System.Web;

using System.Web.UI;

using System.Web.UI.WebControls;

using W.Common;//这里引用扩展方法所在的命名空间

 

namespace webtest

{

    public partial class _Default : System.Web.UI.Page

    {

        protected void Page_Load(object sender, EventArgs e)

        {

            use1();

            Response.Write("<br />");

            use2();

        }

 

        /// <summary>

        /// 没有用扩展方法

        /// </summary>

        private void use1()

        {

            string s = "abc";

            int i = StrToInt(s);

            Response.Write("没有用扩展方法:" + i);

        }

 

        /// <summary>

        /// 使用扩展方法

        /// </summary>

        private void use2()

        {

            string s = "2012";

            int i = s.ToInt();

            Response.Write("使用扩展方法:" + i);

        }

 

        public static int StrToInt(string s)

        {

            int id;

            int.TryParse(s, out id);//这里当转换失败时返回的id为0

            return id;

        }

    }

}

  以上是我对扩展方法理解及使用,如有不对或不足的地方请多多指正,谢谢啦。。

  这我第一次写文章算是排过版的,用好长时间呀,以前都只是看别人的文章,现在才知道写一篇好的文章真的不容易呀。

  努力学习,坚持自己的梦想。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值