今天实现了一个较实用的Pojo(实体)基类

今天实现了一个较实用的Pojo(实体)基类

 

 

呵呵!也许你会觉得就单单重写了Object根类的equals、hashCode、toString这三个方法有什么意义?

实质上,如果你封装过泛型集合基类,并在泛型集合基类中玩过根据自定义属性排序的话,那么你会发现实现这样的一个Pojo基类很有必要!

 

先看看代码的实现:

 

 

 

 

众所周知,String 、Math、还有包装类(如:Integer、Float、Double、Boolean等)都重写了Object的equals方法,这样才使得它们不再比较引用(某些地方也称为“句柄”,“句柄”一词貌似在Windows操作系统中经常使用,如“窗口句柄”),而是比较内容(值)相等。因为,Object的equals()方法比较的是地址值。

 

特别需要注意的是:

Java语言对equals()的要求如下,

• 对称性:如果x.equals(y)返回是“true”,那么y.equals(x)也应该返回是“true”。
• 反射性:x.equals(x)必须返回是“true”。
• 类推性:如果x.equals(y)返回是“true”,而且y.equals(z)返回是“true”,那么z.equals(x)也应该返回是“true”。

• 还有一致性:如果x.equals(y)返回是“true”,只要x和y内容一直不变,不管你重复x.equals(y)多少次,返回都是“true”。
• 任何情况下,x.equals(null),永远返回是“false”;x.equals(和x不同类型的对象)永远返回是“false”。

那么,又为什么要重写hashCode方法呢?网上的一些文章中是这样描述的:

 

我们应该先了解java判断两个对象是否相等的规则。

 

在Java的集合中,判断两个对象是否相等的规则是:


首先,判断两个对象的hashCode是否相等;

如果不相等,认为两个对象也不相等;
如果相等,则判断两个对象用equals运算是否相等;
如果不相等,认为两个对象也不相等;
如果相等,认为两个对象相等;

 

我们在equals方法中需要向下转型,效率很低,所以先判断hashCode方法可以提高效率。

 

一般来说,如果你要把一个类的对象放入集合中,那么通常要为其重写equals()方法,让它们比较地址值而不是内容值。特别地,如果要把你的类的对象放入散列中,那么还要重写hashCode()方法;要放到有序容器中,还要重写compareTo()方法。

 

另外,网上也有这样的一段描述:

 

关于在hibernate的pojo类中,重新equals()和hashcode()的问题:
1),重点是equals,重写hashCode只是技术要求(为了提高效率)
2),为什么要重写equals呢,因为在java的集合框架中,是通过equals来判断两个对象是否相等的
3),在hibernate中,经常使用set集合来保存相关对象,而set集合是不允许重复的。我们再来谈谈前面提到在向hashset集合中添加元素时,怎样判断对象是否相同的准则,前面说了两条,其实只要重写equals()这一条也可以。
但当hashset中元素比较多时,或者是重写的equals()方法比较复杂时,我们只用equals()方法进行比较判断,效率也会非常低,所以引入了hashcode()这个方法,只是为了提高效率,但是我觉得这是非常有必要的(所以我们在前面以两条准则来进行hashset的元素是否重复的判断)。
比如可以这样写:
public int hashCode(){
        return 1;

} // 等价于hashcode无效
这样做的效果就是在比较哈希码的时候不能进行判断,因为每个对象返回的哈希码都是1,每次都必须要经过比较equals()方法后才能进行判断是否重复,这当然会引起效率的大大降低。

效率影响的体现可以在hashset、hashmap、hashtable、LinkedHashMap等带hash字样的集合中去测试,这里就不演示了。

 

至于为什么我要重写toString方法,有两点理由:

1、作为hashCode生成算法的一部分,与其内容直接相关,有更好的散列效果。

2、便于获取其子类更详细的内容描述,便于调试,而不是得到诸如“java.lang.Object@757aef”这样让人难以理解的文字内容。

 

 

我自己也编写了一个测例:

 

 

 

 

在Eclipse3.3控制台输出的最终的运行结果为:

 

User1的内容:[true, 25, 2009-04-10 18:39:54.557, 四川隆昌, 邓超, 3]
User2的内容:[true, 25, 2009-04-10 18:39:54.557, 四川隆昌, 邓超, 3]
User1的散列码:524379269
User2的散列码:524379269
测试User1与User2地址(==)相等:false
测试User1与User2内容(equals)相等:true
User3的内容:[false, 22, 2009-04-10 18:39:54.563, 中华人民共和国四川成都, CodingMouse, 6]
User4的内容:[false, 53, 2009-04-10 18:39:54.563, 美利坚合众国纽约市唐人街, Michael Jackson, 13]
User3的散列码:-715569909
User4的散列码:956891732

测试User3与User4地址(==)相等:false
测试User3与User4内容(equals)相等:false

 

 

反正自我感觉挺良好的,如果您觉得有不妥的地方,还烦请帮忙指出为感!

 

 

                                                                                            CodingMouse

                                                                                           2009年4月11日

 

 

 

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值