.net 中的相等性比较
引用相等性和值相等性
// x, y, z 都是引用类型变量
object x = new object();
object y = new object();
object z = x; // 输出 false,x 和 y 不具有引用相等性
Console.WriteLine(object.ReferenceEquals(x, y)); // 输出 true,x 和 z 具有引用相等性
Console.WriteLine(object.ReferenceEquals(x, z)); // 输出 true,x 和自身具有引用相等性
Console.WriteLine(object.ReferenceEquals(x, x));
int i = ;
int j = ;
int k = ; // 输出 false,i 和 j 不具有值相等性
Console.WriteLine(i.Equals(j)); // 输出 true,i 和 k 具有值相等性
Console.WriteLine(i.Equals(k)); // 输出 true,i 和自身具有值相等性
Console.WriteLine(i.Equals(i));
== 和 != 操作符
- 对于字符串以外的引用类型,判断变量是否具有引用相等性
- 对于值类型,判断变量是否具有值相等性
- 对于字符串类型,判断变量是否具有值相等性
Object.ReferenceEquals 静态方法
int i = ; // 输出 false,i 被装箱两次,是两个不同的对象,不具有引用相等性
Console.WriteLine(object.ReferenceEquals(i, i)); // 相当于:
object x = i;
object y = i;
Console.WriteLine(object.ReferenceEquals(x, y));
.net 框架的源码实现中,ReferenceEquals 方法使用 == 操作符进行判断:
[ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
[System.Runtime.Versioning.NonVersionable]
public static bool ReferenceEquals (Object objA, Object objB) {
return objA == objB;
}
代码参考:http://referencesource.microsoft.com/#mscorlib/system/object.cs,4d607d6d56a93c7e
字符串相等性
在 .net 中,字符串是引用类型,但 == 运算符和 Equals 方法都使用值相等性对字符串进行比较。默认的比较方式是区分大小写的,有时我们希望进行不区分大小写的比较。因此 String 类还有一个 Equals 方法的重载,允许指定如何对字符串进行相等性比较:
public bool Equals(string value, StringComparison comparisonType)
StringComparison 参数允许指定要使用的区域性、大小写和排序规则。
字符串的例子提示相等性比较不是绝对的,两个相同的对象,可能在一个上下文中相等,而在另一个上下文中不相等。
Object.Equals 实例方法
public virtual bool Equals(Object obj)
这是一个虚方法,具体行为取决于是否进行了重写。Object 中 Equals 方法的实现是,如果参数 obj 与当前对象是同一实例,则返回 true。
ValueType 重写了 Equals 方法:若两个值类型变量的类型相同,并且所有实例字段相等,则它们具有值相等性。ValueType 中的 Equals 方法使用反射实现,对性能略有影响。对于自定义值类型,可考虑重写 Equals 方法避免反射带来的性能损失。
Object.Equals 静态方法
这是实用工具性质的方法,用于判断两个变量是否相等,方法签名是:
public static bool Equals(Object objA, Object objB)
public static bool Equals(Object objA, Object objB)
{
if (objA == objB)
{
return true;
}
if (objA == null || objB == null)
{
return false;
}
return objA.Equals(objB);
}
重写 Object.Equals 实例方法
重写 Object.Equals 实例方法时,应遵循以下规则:
- 自反:x.Equals(x) 应返回 true
- 对称:x.Equals(y) 和 y.Equals(x) 应具有相同的结果
- 传递:如果 x.Equals(y) 为 true,并且 y.Equals(z) 为 true,那么 x.Equals(z) 应为 true
- 稳定:如果 x 和 y 未修改,那么连续调用 x.Equals(y) 应具有相同的结果
- 当实参为 null 时,应始终返回 null。
- 若重写 Equals 方法,那么还应重写 GetHashCode 方法,并且,两个相等对象的 GetHashCode 方法应返回相同的值
IEquatable<T> 泛型接口
IEquatable<T> 定义类型特定的相等性比较方法,此接口只定义了一个方法,签名为:
bool Equals(T other)
此接口是从 .net 2.0 开始伴随泛型集合引入的。在泛型集合上调用 Contains、IndexOf、LastIndexOf 和 Remove 等方法时,将使用此接口进行相等性比较。根据 MSDN 的说明,任何可能存储在泛型集合中的类都应实现此接口。
如果实现了 IEquatable 接口,还应重写 Object.Equals 实例方法和 Object.GetHashCode 方法。
IEqualityComparer<T> 泛型接口和 EqualityComparer<T> 泛型类
IEqualityComparer 声明了两个方法:
bool Equals(T x, T y)
int GetHashCode(T obj)
此接口允许在泛型集合中跳过 T 本身的 Equals 和 GetHashCode 实现,如果向泛型集合提供了 IEqualityComparer<T> 的实例,那么集合将使用 IEqualityComparer<T> 的 Equals 和 GetHashCode 方法进行比较。
EqualityComparer<T> 为 IEqualityComparer<T> 泛型接口的实现提供基类。EqualityComparer<T>.Default 属性返回默认的相等性比较器,IEquatable<T> 与泛型集合的配合实际上是在这里起作用的:
- 若 T 实现了 IEquatable<T> 接口,则 EqualityComparer<T>.Default 使用 IEquatable<T> 接口进行相等性比较
- 否则,EqualityComparer<T>.Default 使用 Object.Equals 进行相等性比较
.net 中的相等性比较的更多相关文章
- spring中的传播性 个人认为就是对方法的设置 其作用能传播到里面包含的方法上
spring中的传播性 个人认为就是对方法的设置 其作用能传播到里面包含的方法上
- 如何在Django模型中管理并发性 orm select_for_update
如何在Django模型中管理并发性 为单用户服务的桌面系统的日子已经过去了 - 网络应用程序现在正在为数百万用户提供服务,许多用户出现了广泛的新问题 - 并发问题. 在本文中,我将介绍在Django模 ...
- 【软件构造】第三章第五节 ADT和OOP中的等价性
第三章第五节 ADT和OOP中的等价性 在很多场景下,需要判定两个对象是否 “相等”,例如:判断某个Collection 中是否包含特定元素. ==和equals()有和区别?如何为自定义 ADT正确 ...
- Flume-NG中Transaction并发性探究
我们曾经在Flume-NG中的Channel与Transaction关系(原创)这篇文章中说了channel和Transaction的关系,但是在source和sink中都会使用Transaction ...
- 探究CSS中的包裹性
之前一直都知道css中的部分元素具有包裹性,今天写博客的时候正好也遇到了一个,所以想总结一下,有错误的地方欢迎指出来. 什么是包裹性? 包裹性就是父元素的宽度会收缩到和内部元素宽度一样. 哪些元素具有 ...
- css中的层叠性及权重的比较
假如同一个标签被多个选择器选中,每个选择器都设置了相同的样式,浏览器中加载时这个样式听谁的? 不同选择器设置的同一个样式,只会选择一个进行加载,不会叠加. 为了解决听谁的问题,引入层叠性的概念. 层叠 ...
- 前端设计师如何提高UI界面中的阅读性
阅读体验是ui设计中必不可少的一项,良好的设计应该都是可读的设计,如果信息都无法正常而清晰的传达,那么设计就失去了意义.设计的可读性和排版设计息息相关,这也就跟设计师的设计功底息息相关.下面简单介绍文 ...
- JavaScript中各存在性函数
JavaScript中有很多表示存在性和从属关系的函数,本文介绍如下几个: 1)有关实例与构造函数原型之间的关系:isPrototypeOf(),Object.getPrototypeOf(); 2) ...
- JS中的相等性判断===, ==, Object.is()
首发地址:http://www.geeee.top/2019/11/15/equality-comparisons/,转载请注明出处 相信刚接触JS的人都会被他的想等性判断给整糊涂,看看下面代码,你能 ...
随机推荐
- 地理位置 API
js获取地理位置的接口navigator.geolocation geolocation对象有三个方法 1.getCurrentPosition 2.watchPosition 3.clearWatc ...
- 全景智慧城市常诚——没接触过VR全景的你就是目前VR最大的新闻
据调查,自2015年开始,VR(虚拟现实)技术在传媒行业中的应用呈现井喷式增长,各大国际主流媒体纷纷在新闻报道中使用VR技术.国内运用VR报道新闻最早在2015年12月,财新网利用VR技术对深圳山体垮 ...
- [HDU1004] Let the balloon rise - 让气球升起来
Problem Description Contest time again! How excited it is to see balloons floating around. But to te ...
- 【2017-06-02】Jquery基础
Jquery就是Js集成的一些方法包. 注意:Jquery的引入位置在<head></head>里. 一.选择器 1.Id选择器 $("#div1") 2. ...
- (转)java匿名内部类详解
原文:http://android.blog.51cto.com/268543/384844/ 内部类是指在一个外部类的内部再定义一个类.类名不需要和文件夹相同. *内部类可以是静态static的 ...
- ASP.NET MVC5(一):ASP.NET MVC概览
ASP.NET MVC概览 ASP.NET MVC是一种构建Web应用程序的框架,它将一般的MVC(Model-View-Controller)模式应用于ASP.NET框架. 1.ASP.NET MV ...
- 脑洞大开--一条项目中常用的linux命令引发的经典算法题
小时候家里定了<读者>的月刊,里面记录一个故事:说有有个偏僻的乡村一日突然来了一个美女,她携着万贯家财子女在当地安家落户,成了当地的乡绅.她让她的子女世世代代的保守这个秘密,直到这个秘密不 ...
- maven无法加载本地jar包以及maven项目打包后本地jar包没有打进项目的问题解决办法
1.首先设置依赖项,这样maven就会把该路径下的jar包导入项目引用 <dependency> <groupId>DPSDK-Manager</groupId> ...
- cocoapod升级
1.0 重新安装问题 cd /user/xx/.cocoapod/repos rm -rf master pod setup /user/xx/.cocoapod/repos 查看目录文件夹大小: d ...
- Ext表格分页
pageSize:配置表格或者数据的数量, autoLoad: { start: 0, limit: 2 }:自动加载时候的参数, proxy中:params: {start: 0,limit: 2} ...