码迷,mamicode.com
首页 > Windows程序 > 详细

C# 相等运算

时间:2015-12-09 23:06:13      阅读:253      评论:0      收藏:0      [点我收藏+]

标签:

1. public static bool ReferenceEquals(object left, object right)

Object.ReferenceEquals()在两个变量引用到同一个对象时返回true,也就是两个变量具有相同的对象ID。不管比较的类型是引用类型还是值类型的,这个方法总是检测对象ID,而不是对象内容。

string a = "test";
string b = "test";
if (Object.ReferenceEquals(a, b))
{
    Console.WriteLine("equal");
}
else
{
    Console.WriteLine("not equal");
}
//equal

当比对两个值类型的时候,Object.ReferenceEquals返回false,即使比较的是同一个值类型对象,也会返回false,因为Object.ReferenceEquals输入的两个参数是object类型,所以需要对两个值类型的参数进行装箱操作,导致两个对象的ID不同。

int i = 5;
int j = 5;
if (Object.ReferenceEquals(i, j))
{
    Console.WriteLine("equal");
}
else
{
    Console.WriteLine("not equal");
}
//not equal

if (Object.ReferenceEquals(i, i))
{
    Console.WriteLine("ReferenceEquals : equal");
}
else
{
    Console.WriteLine("ReferenceEquals : not equal");
}
//not equal

2.public virtual bool Equals(object right)

Object.Equals()方法使用对象的ID来断定两个变量是否相等。这个默认的Object.Equals()函数的行为与Object.ReferenceEquals()是一样的。但是请注意,值类型是不一样的。System.ValueType并没有重载Object.Equals(),记住,System.ValueType是所有你所创建的值类型(使用关键字struct创建)的基类。两个值类型的变量相等的前提条件是它们的类型和内容都是一样的。ValueType.Equals()实现了这一行为。不幸的是,ValueType.Equals()并不是一个高效的实现。ValueType.Equals()是所有值类型的基类(译注:这里是说这个方法在基类上进行比较)。为了提供正确的行为,它必须比较派生类的所有成员变量,而且是在不知道派生类的类型的情况下。在C#里,这就意味着要使用反射。对反射而言它们有太多的不利之处,特别是在以性能为目标的时候。

当你想改变引用类型默认的Equals()语义试,建议重载Equ()方法。

你必须确保你重新定义的方法能满足数学相等性质:相等的自反性,对称性和传递性。自反性就是说一个对象是等于它自己的,不管对于什么类型,a==a总应该返回true;对称就是说,如果有a==b为真,那么b==a也必须为真;传递性就是说,如果a==b为真,且b==c也为真,那么a==c也必须为真,这就是传递性。

标准模式:

public class Foo
{
    public override bool Equals(object right)
    {
        // check null:
        // the this pointer is never null in C# methods.
        if (right == null)
        return false;
        if (object.ReferenceEquals(this, right))
        return true;
        // Discussed below.
        if (this.GetType() != right.GetType())
        return false;
        // Compare this type‘s contents here:
        return CompareFooMembers(
        this, right as Foo);
     }
     private static bool CompareFooMembers(Foo f, Foo b)
     {
        //do
     }
}                            

3.== 操作符

 任何时候你创建一个值类型,重新定义操作符==()。原因和实例的Equals()是完全一样的。默认的版本使用的是引用的比较来比较两个值类型。

4.public static bool Equals(object left, object right);

静态的Object.Equals()方法是像下面这样实现的:

public static bool Equals(object left, object right)
{
    // Check object identity
    if (left == right)
    return true;
    // both null references handled above
    if ((left == null) || (right == null))
    return false;
    return left.Equals (right);
}

静态的Equals()是使用左边参数实例的Equals()方法来断定两个对象是否相等。

 

总结

你应该为了更好的性能而总是为值类型实例提供重载的Equals()方法和操作符==()。当你希望引用类型的相等与对象ID的相等不同时,你应该重载引用类型实例的Equals()。

 

C# 相等运算

标签:

原文地址:http://www.cnblogs.com/xanadu123/p/5034405.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!