18.C#扩展方法(十章10.1-10.2)
今天的话题,我们来聊下扩展方法,自己也真心感叹自己的文笔,那叫一个惨啊,回顾写的文章,看着看着也忘记当时是怀着什么心态写的,哈哈,现代人真心是太随性了,可能也是太冷漠了,接着写的吧,总是会有帮助,也会有收获的。
扩展方法是从C#3开始出现在我们的眼前,它即有静态方法的优点,也使我们的代码更具可读性,可以像实例方法一样调用静态方法。在扩展方法没有出现前,我们在代码中常常出现静态的工具类(当然,即使现在我们来会使用静态工具类,那都是前人的智慧结晶),如一个字符串帮助类、时间转换工具类。想像一下,当我们得到一个封装好的类库,里面的源代码是不可见,我们只是类库的使用者,但类库的开发者也不是十全十美的思路,总是会有一些遗漏。我们拿简单的来说,比如现在我拿到一份代码,代码中有一个Room类,如下:
1 class Room 2 { 3 public string Name { get; set; } 4 }
上面的代码是不能修改的,想象一个我们可以使用什么方法给对象的Name属性赋值?我们可以使用实例一个Room对象,直接赋值,但现在我想给Room类加一个SetName的方法,那扩展方法会帮助到我们。如:
1 static class RoomExt 2 { 3 public static void SetName(this Room room, string name) 4 { 5 room.Name = name; 6 } 7 } 8 9 Room room = new Room(); 10 room.Name = "草堂"; 11 Console.WriteLine(room.Name); 12 room.SetName("澡堂"); 13 Console.WriteLine(room.Name); 14 Console.ReadKey();
上述代码中,SetName方法就是Room类的扩展方法,可以像调用实例方法一样调用它。Room类的开发者忘记给Room类增加一个SetName方法,那我们就使用扩展方法给Room类加一个方法,调用的方式和实例方法一样。SetName的第一个参数为扩展类型,指定要扩展的类,并使用关键字this,规定而已,请遵守之。方法的修饰符为static,呵呵,遵守之。如果我们写的代码是外部调用的话,请使用public关键字,使用pirvate关键字,那就只能在为其扩展的扩展方法中才能使用。
1 room.SetName("澡堂"); //调用SetName方法,内部会实现为RoomExt.setName(room,"澡堂")
上面的代码是不是和我们的静态工具一样,是的,使用扩展方法,可以使用代码更具可读性。当然上述的代码只是一个简单使用,在我们正常使用中,自己写的类肯定会加入合适的实例方法,即使是类库的,那也会让类库开发者加一个方法。但如果是微软的开发者没给出合适的方法,没办法,自己加吧。所以扩展方法经常被我们用来扩展系统类型的方法。扩展方法类似静态方法,但它也必须要具有以下的特征:
- 它必须在一个非嵌套的、非泛型的静态类中,如RoomExt类
- 它至少要有一个参数
- 第一个参数不能使用其它修饰符(ref和out)
- 第一个参数必须使用this关键字修饰
- 第一个参数的类型不能是指针类型
找到合适的方法
当我们使用SetName时,会先在实例方法中找,是否有这个方法,如果没有,会从引入的命名空间中找签名符合的方法,也有可能全有重载情况发生,那基于"谁更优"找到方法并执行。
对空类型进行扩展
实际上是对object对象进行扩展,如
1 static class objectExt 2 { 3 public static bool IsNull(this object o) 4 { 5 return o == null; 6 } 7 }
使用如下:
1 static class objectExt 2 { 3 public static bool IsNull(this object o) 4 { 5 return o == null; 6 } 7 } 8 9 10 Room room1 = null; 11 Console.WriteLine(room1.IsNull());
使用是不是很生动,如果你愿意也可以在类中加一个实例方法IsNull,或者使用静态工具来判断一个实例是否为null。实例方法我扩展方法是可以重载的,如
1 class Room 2 { 3 public string Name { get; set; } 4 5 public bool IsNull() 6 { 7 return this == null; 8 } 9 }
在Room类中加一个实例方法IsNull,那当调用IsNul时,永远也调用不到扩展方法,记住上面说的"找方法"的顺序。
请斧正。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?