写点什么

使用扩展方法对调用进行验证

  • 2009-03-27
  • 本文字数:1347 字

    阅读完需:约 4 分钟

利用 C# 3.0 提供的扩展方法技术,可以为已经编译好的程序集类型增加新的方法,从而应对新的扩展。除了在可扩展性方面所具有的优势之外,如果能够合理地结合泛型与类型推断,扩展方法还可以有效降低代码的重复,提高程序的可重用性。例如,这样的方法实现:
public class CustomerDAL
{
public IEnumerable FindCustomers(string roleName)
{
return from customer
in context.Customer
where customer.RoleName.Equals(roleName)
select customer;
}
} 调用如下方法,可能抛出 NullReferenceException 异常:

Customer customer = new CustomerDAL().FindCustomers(Role.Admin).First(); 我们需要对返回结果进行验证,如果返回为 null,则可以抛出自定义异常,或者创建一个空对象,例如:

public IEnumerable FindCustomers(string roleName)
{
IEnumerable customers = from customer
in context.Customer
where customer.RoleName.Equals(roleName)
select customer;
if (customers == null)
{
throw new MyException(“Cann’t find the customers.”);
}
return customers;
} 如果系统有许多方法都需要对返回结果进行验证,则这样的验证逻辑就会充斥在各个方法体中,既不利于重用,也会对未来的修改造成极大的阻碍。当然,我们可以引入 Null Object 模式来替代对 null 值的判断逻辑,但这种方式仍然需要为多种类型定义不同的 Null Object 类型。

Craig Andera 在其博客文章中提出使用扩展方法对调用进行验证。他写道:

NullReferenceException 异常会抛出,但是我们希望有更具体的异常信息。因此,我们编写了如下的扩展方法:

public static T OrThrow(this T obj, Exception e) {
if (obj == null) {
throw e;
}
return obj;
}

利用 OrThrow 扩展方法,则之前的调用方式可以修改为:

Customer customer = new CustomerDAL().FindCustomers(Role.Admin).OrThrow(new MyException(“Can’t find Customer”)).First();

Craig Andera 提出:

OrThrow 扩展方法对于你所要调用的类型而言是通用的,并且它返回了该类型,所以你可以将其插入到表达式链中,而不会丢失智能感应功能。并且因为类型推断功能,实际上并不需要指定具体的类型。

也就是说,OrThrow 扩展方法可以应用到任何类型上,因此它可以在各种类型上重用非空验证甚至是调用验证。借鉴这一思想,我们还可以利用此方法默认实现对象实例的创建,以避免抛出 NullReferenceException 异常,例如:
public static T Instance(this T obj) where T:new()
{
if (obj == null)
{
obj = new T();
}

return obj;
}

由于 Instance 扩展方法中的类型参数 T 需要创建实例,因此必须添加 new() 约束。所以该扩展方法存在一定的局限,例如无法应用在之前的 IEnumerable 类型上。但对于如下的方法却非常有效:
public class ListObject
{
public List Foo()
{
return null;
}
}

通过 Instance 扩展方法,可以安全地调用 List 的相关属性和方法,例如 Count 属性:
Console.WriteLine(new ListObject().Foo().Instance().Count);

控制台打印出来的结果为 0。如果没有 Instance 扩展方法,则会抛出 NullReferenceException 异常。

作为 C# 3.0 增加的新特性,扩展方法在大量项目中得到了广泛地应用,但绝不仅仅是提高可扩展性这么简单。在进行项目开发时,若能适当地考虑使用扩展方法,说不定会带来出奇制胜的效果。

2009-03-27 21:491884
用户头像

发布了 109 篇内容, 共 43.9 次阅读, 收获喜欢 14 次。

关注

评论

发布
暂无评论
发现更多内容

浅谈互联网系统监控体系

老农小江

互联网 微服务 监控

南京水务:通过推进全面预算、财务共享等数智化转型,探寻业财融合

用友BIP

业财融合

关于征集金融业人工智能平台标准参编单位的通知

中国信通院AI Infra工作组

Intellij IDEA快捷键大全(超详细)

小齐写代码

华为云API对话机器人CBS的魅力—实现简单的对话操作

平平无奇爱好科技

Spring Boot 项目中 Bean 注入的方式介绍

Apifox

Java Spring Boot annotation bean Spring Boot bean

Mac上常用的视频编辑软件DaVinci Resolve Studio 18

展初云

Mac软件 视频编辑软件 达芬奇18

如何通过高级流量管理提高 Kubernetes 的弹性

NGINX开源社区

Kubernetes 微服务 nginx 开源版

华为云API文字识别OCR的高效性—AI中名副其实的电子眼

平平无奇爱好科技

Hadoop 集群间同步数据的最佳实践

冰心的小屋

hadoop kerberos hadoop distcp

Databend join reorder 策略

Databend

办公必备Microsoft 365 for Mac(原Office 365)

展初云

Office Mac软件

华为云API图像识别Image的趣味性—AI识别迈克尔·杰克逊

平平无奇爱好科技

关于征集人工智能训练芯片标准参编单位的通知

中国信通院AI Infra工作组

华为云API对话机器人CBS的魅力—要是有AI,我要做“李白”- 5分钟开发作诗机器人

平平无奇爱好科技

SRE实战:如何低成本推进风险治理?稳定性与架构优化的3个策略

TakinTalks稳定性社区

用友BIP,助力装备制造企业数智化转型

用友BIP

制造 数智化

九章云极DataCanvas公司入选《AIGC产业链北京专精特新企业图谱》

九章云极DataCanvas

比特币有助减少腐败;微软 Copilot 每月赔 20 美元;AIGC 明年会“洗冷水澡”丨 RTE 开发者日报 Vol.64

声网

客服订单详情页体验升级之路

得物技术

性能优化 前端 客服业务

英特尔锐炫家族迎新成员:锐炫A580兼顾价格与性能的全新选择

E科讯

全功能笔记工具:Keep It激活最新版

胖墩儿不胖y

Mac软件 笔记工具

关于征集《人工智能开发平台通用能力要求 第4部分:大模型技术要求》标准参编单位及参与专家的通知

中国信通院AI Infra工作组

华为云智能化组装式交付方案 | 金融级PaaS业务洞察及Web3实践的卓越贡献

平平无奇爱好科技

基于Effect的组件设计 | 京东云技术团队

京东科技开发者

前端 React Hooks 企业号10月PK榜 effect

软件测试/测试开发丨为什么接口自动化测试是提升职业技能的关键

测试人

Python 程序员 软件测试 接口测试 接口自动化

ToB企业的财务核算利器——智能收款认领中心!

用友BIP

智能收款

可信AI评估 | 机器学习平台标准解读

中国信通院AI Infra工作组

KubeCon China 2023 | 拥抱开源,华为云原生华彩绽放

华为云开发者联盟

开源 云原生 后端 华为云 华为云开发者联盟

使用扩展方法对调用进行验证_.NET_张逸_InfoQ精选文章