C# 中有两种不同的相等:引用相等和值相等。值相等是大家普遍理解的意义上的相等:它意味着两个对象包含相同的值。例如,两个值为 2 的整数具有值相等性。引用相等意味着要比较的不是两个对象,而是两个对象引用,这两个对象引用引用的是同一个对象。这可以通过简单的赋值来实现,如下面

System.Object a = new System.Object();
System.Object b = a;
System.Object.ReferenceEquals(a, b); //returns true

在上面的代码中,只存在一个对象,但存在对该对象的多个引用:a 和 b。由于它们引用的是同一个对象,因此具有引用相等性。如果两个对象具有引用相等性,则它们也具有值相等性,但是值相等性不能保证引用相等性。

若要检查引用相等性,应使用 ReferenceEquals

1、比较引用类型相等性

System.Object定义了3个不同方法,来比较对象的相等性:ReferenceEquals()和两个版本的Equals()。再加上比较运算符(==)

ReferenceEquals(),静态方法,不能被重写,测试两个引用是否引用类的同一个实例,特别是两个引用是否包含相同的地址。
如果提供的两个引用引用同一个对象实例,则ReferenceEquals()总是返回true,否则返回false,但是他认为null等于null:

System.Object a = new System.Object();
System.Object b = a;
System.Object c=new System.Object();
System.Object.ReferenceEquals(a, b); //returns true
bool flag=ReferenceEquals(null,null) //return true
bool flag1=ReferenceEquals(a,c) //return false
bool flag2=ReferenceEquals(null,a) //return false

另外,ReferenceEquals()在应用于值类型是,他总是返回false,因为为了调用这个方法,值类型需要装箱到对象中,
即使使用下面的代码:

bool flag=ReferenceEquals(v,v);  //v是值类型

也会返回false,应为在转换每个参数时,v都会被单独装箱,这意味着会得到不同的引用,也就是说ReferenceEquals() 来比较值类型
实际上没什么意义。

2、静态的Object.Equals(Object objA,Object objB)方法

如果如果objA 是与 objB 相同的实例,或者如果两者均为空引用,或者如果 objA.Equals(objB) 返回 true,则为 true;否则为 false。

Equals 的默认实现仅支持引用相等,但派生类可重写此方法以支持值相等。
对于引用类型,相等定义为对象相等;即这些引用是否引用同一对象。对于值类型,相等定义为按位相等。ValueType 类支持值类型。
在调用 objA.Equals(objB) 前,此方法首先检查两个参数是否均为空引用。

String s1="Hello";
String s2="World";
String s3="Hello"; Object.Equals(s1,s2) //return false
Object.Equals(s1,s3) //return true s2=null;
Object.Equals(s1,s2) //return false s1=null;
s2=null;
Object.Equals(s1,s2) //return true

3、虚拟的 Object.Equals(obj)方法

如果指定的 Object 等于当前的 Object,则为 true;否则为 false。

此方法可由派生类重写。例如,如果两个对象表示相同的值,则许多基数据类型返回 true;否则返回 false。 此方法仅比较基元和对象。若要比较更复杂的结构(如对象数组),必须重写该方法。 下面的语句对于 Equals 方法的所有实现均必须为真。

Equals 的实现必须不引发异常。 对于某些类型的对象,最好让 Equals 测试值相等性而非引用相等性。如果两个对象具有相同的“值”,那么即使它们不是同一实例,这样的 Equals 实现仍返回 true。类型实施者决定对象的“值”的构成,但这通常是存储在对象的实例变量中的部分或全部数据。例如,String 的值基于字符串的字符;对于两个按同样的顺序包含完全相同的字符的字符串实例,String 类的 Equals 方法返回 true

int i=;
int j=;
bool flag=i.Equals(j); //只类型比较,返回true
double k=9.0;
bool flag1=i.Equals(k);// 类型不会自动转换并比较数值,返回false Object objA=new Object();
Object objB=new Object(); bool flag2=objA.Equals(objB); //引用比较,返回false
bool flag3=objA.Equals(String.Empty); //比较对象的类型不同,直接返回false

另外,Microsoft已经在System.ValueType类中重载了实例方法Equals(),以便对值类型进行合适的相等性测试。
如果调用sA.Equals(sB),其中sA和sB是某个结构的实例,则根据sA和sB是否在其所有的字段包含相同的值,而返回true或false

4、==比较运算符

对于值类型 都是比较代数值是否相等。

最好将比较运算符看作严格的值比较和严格的引用比较之间的中间项,在大多数情况下,下面代码表示正在比较引用:
bool b=(x==y) //x和y都是引用类型
在某些情况下,最好重写比较运算符(==),以执行值的比较,例如:System.String类,Microsoft重写了==运算符,用来比较
字符串的内容,而不是比较他们的引用

5、==和Equals异同

相同点: 对于值类型 都是比较代数值是否相等
不同点:(1)对于值类型比较,==会进行类型的自动转换,然后比较代数值,Equals则不会进行转换,先比较类型,再比较值,如果类型不同直接返回false

细说C#的ReferenceEquals,Equals和==比较运算符的更多相关文章

  1. Java提高篇——equals()方法和“==”运算符

    equals() 超类Object中有这个equals()方法,该方法主要用于比较两个对象是否相等.该方法的源码如下: public boolean equals(Object obj) { retu ...

  2. java中的equals方法与"=="运算符解说

    在编程的时候,我们可能经常会用到equals方法,那么这个equals方法和运算符“==”有什么样的区别? public class equal { /** * @param args */ publ ...

  3. C#中==运算符

    在这篇博客中,我们将介绍如下内容: ==运算符与基元类型 ==运算符与引用类型 ==运算符与String类型 ==运算符与值类型 ==运算符与泛型 ==运算符与基元类型 我们分别用两种方式比较两个整数 ...

  4. C#中 Reference Equals, == , Equals的区别

    原文地址:http://blog.csdn.net/wuchen_net/archive/2010/03/23/5409327.aspx ReferenceEquals, == , Equals Eq ...

  5. C#高级编程9-第7章 运算符和类型强制转换

    运算符和类型强制转换 1.运算符 运算符的简化操作 条件运算符: if-else的简化操作,也称三元运算符.如果条件为真,返回一个值,为假返回另外一个值. condition?true_value:f ...

  6. String类中的equals()方法

    在Java中,每一个对象都有一个地址空间,在这空间保存着这个对象的值. equals 比较的是值,==比较的地址以及值. 01: public class StringExample02: {03: ...

  7. 快看Sample代码,速学Swift语言(3)-运算符

    运算符是用来检查,更改或组合值的特殊符号或短语.Swift提供的很多常规的运算符,如+.-.*./.%.=.==等,以及逻辑运算的&&.||等等,基本上不需要重复介绍,我们在这里只需要 ...

  8. [知识库分享系列] 二、.NET(ASP.NET)

    最近时间又有了新的想法,当我用新的眼光在整理一些很老的知识库时,发现很多东西都已经过时,或者是很基础很零碎的知识点.如果分享出去大家不看倒好,更担心的是会误人子弟,但为了保证此系列的完整,还是选择分享 ...

  9. 多个提高C#编程能力的建议

    1.总是用属性 (Property) 来代替可访问的数据成员 2.在 readonly 和 const 之间,优先使用 readonly 3.在 as 和 强制类型转换之间,优先使用 as 操作符 4 ...

随机推荐

  1. spring自带工具类

    在spring-core.jar包中,org.springframework.util package下有很多工具类,这些工具类十分具有参考意义.

  2. 常见的NullPointerException总结

    NullPointerException在这里简称为NPE 通过一些实例总结下常见的NPE问题: 1. 自动拆箱抛NPE 实体类: public class User { private String ...

  3. POJ 2492 A Bug's Life (带权并查集 && 向量偏移)

    题意 : 给你 n 只虫且性别只有公母, 接下来给出 m 个关系, 这 m 个关系中都是代表这两只虫能够交配, 就是默认异性, 问你在给出的关系中有没有与异性交配这一事实相反的, 即同性之间给出了交配 ...

  4. Codeforces Round #345 (Div. 2) E. Table Compression 并查集+智商题

    E. Table Compression time limit per test 4 seconds memory limit per test 256 megabytes input standar ...

  5. Pku2978 Colored stones

    题目链接:Click here Solution: 状压dp,考虑\(f[i][j][k]\)表示当前到了第i个石头,颜色状态为j,选取的最后一个石头颜色为k时能够留下的石头的最大数量 转移也很好转移 ...

  6. jQuery字体图标的三种方法

    BootStrap框架原生图标 在导入BootStrap包的同时,导入bootstrap-3.3.7-dist/css/bootstrap.css层叠样式; <button type=" ...

  7. JAVA语言动手动脑问题

    1. 早期经常这样定义变量  int value=100;前面的示例中这样定义变量  MyClass obj = new MyClass(); 这两种方式定义的变量是一样的吗?   答:不一样,后者开 ...

  8. android 3.0 ationbar使用总结

    1,ationbar的基本讲解 http://www.apkbus.com/forum.php?mod=viewthread&tid=125536 仅仅需要根据需求写出一个menu资源文件 2 ...

  9. Arthas随笔

    目录 Arthas 安装Java 安装 Arthas Arthas 命令及示例 源码分析 Arthas 安装Java 下载jdk 注意 下载的JDK版本要与linux操作系统相匹配,否则汇报No su ...

  10. 1、maven的下载,安装,配置

    下载 1.maven官方下载地址: http://maven.apache.org/download.cgi 进入官网: 下载各历史版本官方地址: https://archive.apache.org ...