本文介绍了使用 JPA 和 Hibernate 时应如何实现 equals 和 hashcode的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

模型类的 equals 和 hashcode 应该如何在 Hibernate 中实现?常见的陷阱有哪些?对于大多数情况,默认实现是否足够好?使用业务密钥有什么意义吗?

How should model class's equals and hashcode be implemented in Hibernate? What are the common pitfalls? Is the default implementation good enough for most cases? Is there any sense to use business keys?

在我看来,当考虑到延迟获取、id 生成、代理等时,很难在每种情况下都正确工作.

It seems to me that it's pretty hard to get it right to work in every situation, when lazy fetching, id generation, proxy, etc are taken into account.

推荐答案

Hibernate 对何时/如何覆盖 equals()/hashCode()文档中

Hibernate has a nice and long description of when / how to override equals() / hashCode() in documentation

它的要点是您只需要担心您的实体是否将成为 Set 的一部分,或者您是否要分离/附加其实例.后者并不常见.前者通常最好通过以下方式处理:

The gist of it is you only need to worry about it if your entity will be part of a Set or if you're going to be detaching / attaching its instances. The latter is not that common. The former is usually best handled via:

  1. 基于业务键的 equals()/hashCode() - 例如在对象(或至少是会话)生命周期内不会更改的独特属性组合.
  2. 如果以上是不可能的,则将 equals()/hashCode() 基于主键,如果它已设置并且对象标识/System.identityHashCode() 否则.重要部分是,在新实体添加到 Set 并持久化之后,您需要重新加载 Set;否则,您最终可能会出现奇怪的行为(最终导致错误和/或数据损坏),因为您的实体可能被分配到与其当前 hashCode() 不匹配的存储桶.
  1. Basing equals() / hashCode() on a business key - e.g. a unique combination of attributes that is not going to change during object (or, at least, session) lifetime.
  2. If the above is impossible, base equals() / hashCode() on primary key IF it's set and object identity / System.identityHashCode() otherwise. The important part here is that you need to reload your Set after new entity has been added to it and persisted; otherwise you may end up with strange behavior (ultimately resulting in errors and / or data corruption) because your entity may be allocated to a bucket not matching its current hashCode().

这篇关于使用 JPA 和 Hibernate 时应如何实现 equals 和 hashcode的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

07-30 14:06