ITPub博客

首页 > Linux操作系统 > Linux操作系统 > .net框架通用对象操作

.net框架通用对象操作

原创 Linux操作系统 作者:iDotNetSpace 时间:2008-09-16 13:10:32 0 删除 编辑
一.对象的等值性和惟一性

 System.Object类型提供了一个Equals的虚方法,其目的为判断两个对象是否有个相同的"值".


<!--

Code highlighting produced by Actipro CodeHighlighter (freeware)
http://www.CodeHighlighter.com/

--> 1 class Object
 2     {
 3         public virtual Boolean Equals(Object obj)
 4         {
 5             //如果两个引用指向的是同一个对象
 6             //它们肯定相等
 7             if(this==obj)
 8             {
 9                 return (true);
10             }
11 
12             return (false);
13  
14         }
15     }

 

这也许是最简单的方法.

但有时间,它提供的默认实现对我们来说是不够的,必须重写Equals方法.

自己写的时候,要遵循以下4条规则:

1.Equals方法必须是自反的.也就是说,x.Equals(x)必须返回true.

2.   Equals方法必须是对称的.也就是说,x.Equals(y)和y.Equals(x)必须返回同样的值.

3.Equals方法必须是可传递的.也就是说,如果x.Equals(y)和y.Equals(z)都返回true,那么x.Equals(z)也必须返回     true.

4. Equals方法必须是前后一致的.也就是说,如果两个对象的值没有发生变化,多次调用Equals方法的返回值应该相同.

(一)为基类没有重写Object.Equals方法的引用类型实现Equals

 


<!--

Code highlighting produced by Actipro CodeHighlighter (freeware)
http://www.CodeHighlighter.com/

-->  class MyRefType:BaseType
    {
        RefType refobj;   
//引用类型
        ValueType valobj;  //值类型

        
public override bool Equals(object obj)
        {
            
//因为‘this’不为null,所以如果obj为null
            
//那么两个对象将不可能相等

            
if (obj == null)
                
return false;

            
//如果两个对象的类型不同,那么它们不可能相等
            if (this.GetType() != obj.GetType())
                
return false;
            
//将obj转型为定义的类型以访问其中的字段,这里的
            
//转型不会失败,因为已经知道两个对象是同一类型

            MyRefType other
=(MyRefType)obj;

            
//比较其中的引用类型字段
            if (!Object.Equals(refobj, other.refobj))
                
return false;

            
//比较其中的值类型字段
            if (!valobj.Equals(other.valobj))
                
return false;

            
return true;  //到这里两个对象才相等
        }
    }

 

这要注意的:

1.要比较引用类型的字段,我们应该调用Object的静态方法Equals方法.

    Objext的静态方法Equals方法是一个比较两个引用类型对象的辅助方法.采用这种方法比较,是因为即使两个字段出现了值为null的情况,代码仍会正常运行.

2.要比较值类型的字段,应该调用该字段类型的Equals方法.不应该调用Object的静态方法Equals方法.因为值类型对象的值永远不可能为null,并且调用Object的静态方法Equals会对值类型对象执行装箱操作.

(二)为基类重写了Object.Equals方法的引用类型实现Equals

 


<!--

Code highlighting produced by Actipro CodeHighlighter (freeware)
http://www.CodeHighlighter.com/

-->class MyRefType:BaseType
    {
        RefType refobj;   
//引用类型
        ValueType valobj;  //值类型

        
public override bool Equals(object obj)
        {
            
//首先让基类型比较其中的字段
            if (!base.Equals(obj))
                
return false;

            
//因为‘this’不为null,所以如果obj为null
            
//那么两个对象将不可能相等

            
if (obj == null)
                
return false;

            
//如果两个对象的类型不同,那么它们不可能相等
            if (this.GetType() != obj.GetType())
                
return false;
            
//将obj转型为定义的类型以访问其中的字段,这里的
            
//转型不会失败,因为已经知道两个对象是同一类型

            MyRefType other
=(MyRefType)obj;

            
//比较其中的引用类型字段
            if (!Object.Equals(refobj, other.refobj))
                
return false;

            
//比较其中的值类型字段
            if (!valobj.Equals(other.valobj))
                
return false;

            
return true;  //到这里两个对象才相等
        }
    }

 

如果调用base.Equals会导致调用Object.Equals方法,那么就不应该再调用它.这一点很重要.因为只有在两个引用指向同一个对象时,Object.Equals方法才会返回true.如果两个引用没有指向同一个对象,那么它将返回false.这样我们实现的Equals方法将总是返回false.

 当然,如果我们定义的类型直接继承自Object,我们就应该象第一段代码那样来实现Equals.如果我们定义的类型不是直接继承自Object,我们必须首先确定该类型的基类型是否重写了Equals方法.如果其中任何一个基类型重写了Equals方法,那么我们就应该象这段代码先base.Equals方法.

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/12639172/viewspace-448573/ ,如需转载,请注明出处,否则将追究法律责任。

下一篇: C#命名规范
请登录后发表评论 登录
全部评论

注册时间:2008-01-04

  • 博文量
    2376
  • 访问量
    5766532