本文翻译自:In C#, what happens when you call an extension method on a null object?

Does the method get called with a null value or does it give a null reference exception? 是使用null值调用方法还是提供null引用异常?

MyObject myObject = null;
myObject.MyExtensionMethod(); // <-- is this a null reference exception?

If this is the case I will never need to check my 'this' parameter for null? 如果是这种情况,我永远不需要检查我的'this'参数是否为null?


#1楼

参考:https://stackoom.com/question/3YOf/在C-中-当您在null对象上调用扩展方法时会发生什么


#2楼

As you've already discovered, since extension methods are simply glorified static methods, they will be called with null references passed in, without a NullReferenceException being thrown. 正如您已经发现的那样,因为扩展方法只是美化的静态方法,所以在传入null引用的情况下调用它们,而不会抛出NullReferenceException But, since they look like instance methods to the caller, they should also behave as such. 但是,因为它们看起来像实例方法来调用者,他们也应该表现为这样。 You should then, most of the time, check the this parameter and throw an exception if it's null . 那么,您应该在大多数情况下检查this参数并在它为null抛出异常。 It's OK not to do this if the method explicitly takes care of null values and its name indicates it duly, like in the examples below: 如果方法显式处理null值并且其名称适当地表示它,则不执行此操作,如下例所示:

public static class StringNullExtensions { public static bool IsNullOrEmpty(this string s) { return string.IsNullOrEmpty(s); } public static bool IsNullOrBlank(this string s) { return s == null || s.Trim().Length == 0; }
}

I've also written a blog post about this some time ago. 我前段时间也写了一篇博文 。


#3楼

As others pointed out, calling an extension method on null reference causes the this argument to be null and nothing else special will happen. 正如其他人所指出的那样,在null引用上调用扩展方法会导致this参数为null,并且不会发生任何其他特殊情况。 This gives raise to an idea to use extension methods to write guard clauses. 这提出了使用扩展方法编写保护子句的想法。

You may read this article for examples: How to Reduce Cyclomatic Complexity: Guard Clause Short version is this: 您可以阅读本文的示例: 如何减少Cyclomatic复杂性:Guard子句短版本是这样的:

public static class StringExtensions
{public static void AssertNonEmpty(this string value, string paramName){if (string.IsNullOrEmpty(value))throw new ArgumentException("Value must be a non-empty string.", paramName);}
}

This is the string class extension method which can be called on null reference: 这是可以在null引用上调用的字符串类扩展方法:

((string)null).AssertNonEmpty("null");

The call works fine only because runtime will successfully call the extension method on null reference. 调用工作正常,因为运行时将成功调用null引用上的扩展方法。 Then you can use this extension method to implement guard clauses without messy syntax: 然后你可以使用这个扩展方法来实现guard子句而不会出现凌乱的语法:

    public IRegisteredUser RegisterUser(string userName, string referrerName){userName.AssertNonEmpty("userName");referrerName.AssertNonEmpty("referrerName");...}

#4楼

That will work fine (no exception). 这样可以正常工作(也不例外)。 Extension methods don't use virtual calls (ie it uses the "call" il instruction, not "callvirt") so there is no null check unless you write it yourself in the extension method. 扩展方法不使用虚拟调用(即它使用“call”il指令,而不是“callvirt”),因此除非您在扩展方法中自己编写,否则不会进行空值检查。 This is actually useful in a few cases: 在少数情况下,这实际上很有用:

public static bool IsNullOrEmpty(this string value)
{return string.IsNullOrEmpty(value);
}
public static void ThrowIfNull<T>(this T obj, string parameterName)where T : class
{if(obj == null) throw new ArgumentNullException(parameterName);
}

etc 等等

Fundamentally, calls to static calls are very literal - ie 从根本上说,对静态调用的调用是非常直接的 - 即

string s = ...
if(s.IsNullOrEmpty()) {...}

becomes: 变为:

string s = ...
if(YourExtensionClass.IsNullOrEmpty(s)) {...}

where there is obviously no null check. 哪里显然没有空检查。


#5楼

extensionmethod是静态的,所以如果你不对这个MyObject做任何事情它应该不是问题,快速测试应该验证它:)


#6楼

A null will be passed to the extension method. null将被传递给扩展方法。

If the method tries to access the object without checking is it null, then yes, it will throw an exception. 如果该方法试图访问该对象而不检查它是否为null,则是,它将引发异常。

A guy here wrote "IsNull" and "IsNotNull" extension methods that check is the reference passed null or not. 这里的一个人写了“IsNull”和“IsNotNull”扩展方法,检查是否传递null。 Personally I think this is an aberration and shouldn't have seen light of day, but it's perfectly valid c#. 就个人而言,我认为这是一种失常,不应该看到日常光,但它是完全有效的c#。

在C#中,当您在null对象上调用扩展方法时会发生什么?相关推荐

  1. JS中数组(Array)、Json对象长度(length)获取方法

    JS中数组(Array).Json对象长度(length)获取方法 1.数组 var array = []; var length = array.length; 2.JSON对象 1)方法1: va ...

  2. php数组包含对象吗,在包含数组的PHP对象上调用方法

    我有一个名为"食物"的PHP类.该类的内部数据结构是一个Array. class Food { public $dataArray;// = array(); public $si ...

  3. php调用成员函数错误,PHP致命错误:在非对象上调用成员函数exec...

    我收到错误PHP致命错误:每当我调用类似的东西时,都在非对象上调用成员函数execute(),该对象引用-.-> execute()行. $select_str = 'select id, st ...

  4. php函数param太多,关于php:在非对象上调用成员函数bind_param()

    本问题已经有最佳答案,请猛点这里访问. 我正在尝试在此准备好的语句中绑定变量,但我一直收到错误: Call to a member function bind_param() on a non-obj ...

  5. 各种对象上的 toString 方法的区别和关联

    各种对象上的 toString 方法的区别和关联 问:请简述一下用于判断数据类型都有哪些方法? 答:巴拉巴拉--小魔仙 在判断数据类型的时候,有一种方式可以清晰直接地区分出所有的数据类型,即 Obje ...

  6. MVC为Html对象建立一个扩展方法,使用自己的控件就像使用TextBox一样方便

    先看一下我想要的结果: 很容易它就是一个单选按钮组,当我后台为Html对象(HtmlHelper的一个实例,它被定义在System.Web.Mvc名称空间下的WebViewPage类,即它对于所有MV ...

  7. javascript中NaN属性、null对象、Number对象、Object对象

    NaN属性: 表示不是一个数字,是全局对象的属性,其初始值为NaN <script>console.log(NaN == NaN); //false</script> null ...

  8. 【超全指南】Java 8 中使用 Optional 处理 null 对象

    作者:超级小豆丁 http://www.mydlq.club/article/88/ 系统环境: Java JDK 版本:1.8 参考地址: Oracle JDK API 参考文档 https://d ...

  9. PHP中 对象自动调用的方法:__set()、__get()、__tostring()

    总结: (1)__get($property_name):获取私有属性$name值时,此对象会自动调用该方法,将属性name值传给参数$property_name,通过这个方法的内部 执行,返回我们传 ...

最新文章

  1. sharding jdbc sql路由日志
  2. Git常见疑难解答集锦
  3. Google平台搭建虚机
  4. WebSocket 中的Netty
  5. Win32 API 枚举打印机
  6. 文件寄生——寄生虫自体繁衍的道路
  7. 9款jQuery插件为你的网站增加亮点
  8. C# 与 Unity 同名函数
  9. mysql 实验_实验二 MySQL 实验.doc
  10. 关于通配泛型类型有几种_5.7 泛型通配符和类型参数的范围
  11. SQL重复记录查询的几种方法
  12. js des加密 java_Java实现与JS相同的Des加解密算法完整实例
  13. 240多个jQuery插件 功能强大 齐全
  14. 学习Unix其实就这样简单
  15. Linux:网络安全与主机基本防护:限制端口, 网络升级与 SELinux
  16. Python学习之路 第3次笔记!
  17. vue设置右边距_数控CNC雕刻机使用系列之二: 维宏软件的参数设置
  18. 使用Arduino,DHT11和IR Blaster的自动交流温度控制器
  19. C++ 万年历、生肖判断、计算第几天
  20. 谷歌,Google,Chrome,检查工具栏常用功能介绍

热门文章

  1. 从单机到集群会话的管理之集群模式一
  2. atitit.激活一个窗口总结 swing java .net php
  3. 今天走了一天, 才回到家
  4. 百度缺的不是狼性,而是鲁滨逊
  5. 【我来解惑】.Net应该学什么怎么学(二)
  6. moosefs-1.6.10 安装手记
  7. 《python可以这样学》第一章
  8. [python] 1.解释器
  9. 自定义标签TLD文件中,rtexprvalue子标签的意思
  10. Python - 列表解析式/生成器表达式