情况toString()不同,你可以随心所欲,toString()所以我只会覆盖equals()(和hashCode()).
首先,规则:如果你想存储对象的List,Map或Set 则是一个要求equals 和hashCode实施,使他们遵守的标准合同文件中指定.
现在,如何实施equals()和hashCode()?一个"自然"的想法是使用映射的属性Id作为以下内容的一部分equals():
public class User {
...
public boolean equals(Object other) {
if (this==other) return true;
if (id==null) return false;
if ( !(other instanceof User) ) return false;
final User that = (User) other;
return this.id.equals( that.getId() );
}
public int hashCode() {
return id==null ? System.identityHashCode(this) : id.hashCode();
}
}
Run Code Online (Sandbox Code Playgroud)
不幸的是,这个解决方案有一个主要问题:当使用生成的标识符时,在实体变为持久化之前不会分配这些值,因此如果在保存之前将瞬态实体添加到a Set中,则其哈希代码将在其中进行更改Set并且会中断合同Set.
因此,推荐的方法是使用属于业务键的属性,即对于具有相同数据库标识的每个实例唯一的属性组合.例如,对于User类,这可以是用户名:
public class User {
...
public boolean equals(Object other) {
if (this==other) return true;
if ( !(other instanceof User) ) return false;
final User that = (User) other;
return this.username.equals( that.getUsername() );
}
public int hashCode() {
return username.hashCode();
}
}
Run Code Online (Sandbox Code Playgroud)
Hibernate参考文档总结如下:
" 永远不要使用数据库标识符来实现相等性;使用业务键,唯一的,通常是不可变的属性的组合.如果瞬态对象是持久的,数据库标识符将会改变.如果瞬态实例(通常与分离的实例一起)是保存在a中
Set,更改hashcode中断的合同Set.业务键的属性不必像数据库主键一样稳定,只要对象在同一个Set中,就必须保证稳定性.- 12.1.3.考虑对象身份" 建议您实现
equals()和hashCode()使用Business密钥相等.业务密钥相等意味着该equals()方法仅比较构成业务密钥的属性.它是识别我们在现实世界中的实例的密钥(自然候选密钥)" - 4.3.实现equals()和hashCode()
那么,回到最初的问题:
@Transient属性很可能不属于这样一个关键.List,Map,Set.| 归档时间: |
|
| 查看次数: |
2778 次 |
| 最近记录: |