C#学习笔记第四篇之Equals,GetHashCode ,ToString函数深度剖析(二)
来源:互联网 发布:怎么下载淘宝网 编辑:程序博客网 时间:2024/06/06 00:36
C#学习笔记第四篇之Equals,GetHashCode ,ToString函数深度剖析(二)
上一篇详细搞了Equals,这一篇重点说下GetHashCode函数有什么用,怎么用,在哪里用,用的时候注意什么。
然后简要说下ToString的意义所在,因为比较简单,就不详细说明了。
1、GetHashCode函数有什么用?
依然参考官网的一句话来解释,“A hash code is a numeric value that is used to insert and identify an object in a hash-based collection such as the Dictionary<TKey, TValue> class”,大意就是说,HashCode就是来确定一个对象的唯一值,被用来当做那些运用了hash查找的容器或者函数来进行插入或者唯一的确定查找。
更通俗的讲,就是,一个对象,当把这个对象添加到一个键值对这样的容器(如Dictionary<Key,Value>)时,可以调用该对象的这个函数来得到一个唯一的HashCode(相当于一个对象的整数ID),把该值放入键值对容器中作为唯一的键值,可以进行查找,插入操作。
再具体点讲,就是,当我们放入两个相同的对象如 string s1 = “aaa” ;string s2 = "aaa";,s1,s2放入Dictionary中时,我们知道Dictionary是不允许Key值相等的,那么s1,s2,放入其中,他们的key时多少?如何得到这个key?对的,这个时候,GetHashCode函数就派上用场了,这个Dictionary就会调用这两个对象的GetHashCode函数来得到两个HashCode值,其实GetHashCode就是一个hash函数,把对象映射成唯一的一个对象ID,便于我们在把对象放入利用了hash映射的容器时,这些容器能得到每个对象的hash值,别的地方还真用不上呢。
2、这个函数是怎么工作的?
因为每个类的父类都是Object类,所以定义的每个类中都默认有个继承的方法GetHashCode,当然你完全可以重写它。(有些时候还必须重写,这正是本文重点说明的地方,因为默认的父类hashCode的值,是基于父类的引用值)
其实就是一hash函数,来产生一个值,然后返回,作为这个对象唯一的一个Id。
3、怎么用?
通常只需要在对象中重写就行了,但是要注意的是,该值一定要确保唯一,不要发生重复。如果重复的结果就是两个不同的对象对应了同一个相同的Id(hashcode),这显然不是我们想要的。
public override int GetHashCode() { return Tuple.Create(x, y).GetHashCode(); }
Tuple是一个序列化数组,创建x,y,序列数组,这是官网提供的一种hash映射方式,当然你可以发挥想象尽可能的确保x与y的计算组合值一定时,x与y也相同,因为我们要保证hashcode一样,那么两个类也相同,同时也引出了下一条注意事项就是,重写了hashcode这个函数,也一定要重写Equals这个函数,并且确保hash值也是一样的,不然相同的类对应不同的hashcode,多蛋疼啊。
If you override the GetHashCode method, you should also override Equals, and vice versa. If your overridden Equals method returns true when two objects are tested for equality, your overriddenGetHashCode method must return the same value for the two objects.
If an object that is used as a key in a hash table does not provide a useful implementation of GetHashCode, you can specify a hash code provider by supplying an IEqualityComparer implementation to one of the overloads of the Hashtable class constructor。
官网的解释是:要保证两个相等的对象有唯一的一个hashcode值,(这当然是必须的啊!)保持语义的一致性。
所以一个完整的应该是:
public class DaichoKey : IEquatable<DaichoKey>{ public int ID { get; set; } public int SubID { get; set; } public bool Equals(DaichoKey other) { return this.ID == other.ID && this.SubID == other.SubID; } public override bool Equals(object obj) { if (obj == null) return base.Equals(obj); if (obj is DaichoKey) return Equals(obj as DaichoKey); else throw new InvalidCastException("the 'obj' Argument is not a DaichoKey object"); } public override int GetHashCode() { return base.GetHashCode();//return object's hashcode }}
另外要说的是,不仅仅是Dictionary这类容器,才需要重写该函数,更重要的是,凡是要利用类的hashcode来作为key值来进行查找的函数都要重写,譬如说List,虽然是个线性表,但是它的函数Contains,IndexOf函数,都是利用类的hashcode值,来hash映射查找的,所以如果要加入List的中类,没有实现GetHashCode函数,它调用Contains和IndexOf函数时,相同的类对象,但它会找不到的。更为细节的讨论,请看专题你要小心的GetHashCode这篇文章有详细的解释。
4、ToString作用?
就是不想干巴巴的得到一个类的名字,当想把一个类的各个属性值都取得并用于打印或者其他用途是,返回一个类的字符串比返回一个类的引用值要有用的多。
- C#学习笔记第四篇之Equals,GetHashCode ,ToString函数深度剖析(二)
- C#学习笔记第四篇之Equals,GetHashCode ,ToString函数深度剖析(一)
- <<C语言深度剖析>>学习笔记之二:关键字详解
- c语言深度剖析之学习笔记(二)------------符号
- GetHashCode方法学习笔记
- C#之GetHashCode() 和Equal()
- equals&&hashCode&&toString函数
- <<C语言深度剖析>>学习之七之函数
- C语言深度剖析学习笔记-指针、数组、内存、函数
- Boost学习笔记之六 深度剖析pool
- <<C语言深度剖析>>学习笔记之三:符号
- Java学习笔记五:Object类,equals ==,toString
- C++学习笔记(第四章 函数的应用及多文件组织 之二)
- An article about Equals and GetHashCode functions in C#
- An article about Equals and GetHashCode functions in C#
- Effective C#阅读笔记-7GetHashCode陷阱
- Java学习之equals()、hashCode()、identityHashCode()、toString()和==
- C#学习之ToString()和Convert.ToString()的用法区别
- 免费WiFi等你来上钩
- 分解质因数算法
- launcher 解读之一
- pgbench 测试 pgxc
- 关于521
- C#学习笔记第四篇之Equals,GetHashCode ,ToString函数深度剖析(二)
- ubuntu 14.04 恢复系统默认中文字体
- java并发编程--互斥锁, 读写锁及条件
- nlpir分词工具使用记录
- 备份及还原Xcode的模拟器
- 基于jquery实现的弹出层效果实现!
- 从毕业生到企业IT主管的历程
- uva 10161 Ant on a Chessboard(数学推规律)
- 启动 Eclipse 有“Failed to load the JNI shared library jvm.dll” 错误提示