Java 循环等于()会导致堆栈溢出

Java 循环等于()会导致堆栈溢出,java,hibernate,jakarta-ee,equals,Java,Hibernate,Jakarta Ee,Equals,我正在使用hibernate并具有双向关系。如何正确重写这两个类的equals() 下面是代码(使用guava对象):(PS:这是一个糟糕的示例,是对实体的选择,但我有兴趣学习推荐的方法) 目的地: @Entity @Table(name = "DESTINATION") public class Destination{ private Integer id; private String name; private Set<DestinationAlias>

我正在使用hibernate并具有双向关系。如何正确重写这两个类的equals()

下面是代码(使用guava对象):(PS:这是一个糟糕的示例,是对实体的选择,但我有兴趣学习推荐的方法)

目的地

@Entity
@Table(name = "DESTINATION")
public class Destination{
    private Integer id;
    private String name;
    private Set<DestinationAlias> aliases = new HashSet<DestinationAlias>(0);


    @Override
    public boolean equals(Object obj) {
        if(obj == this) return true;

        if(obj instanceof Destination){
            final Destination otherDestination = (Destination) obj;
            return Objects.equal(getName().toUpperCase(), otherDestination.getName().toUpperCase()) 
                    && Objects.equal(getAliases(), otherDestination.getAliases());
        }
        return false;
    }
}
@Entity
@Table(name = "DESTINATIONALIAS")
public final class DestinationAlias {
    private Integer idDestinationAlias;
    private String alias;   
    private Destination mainCity;

    @Override
    public boolean equals(Object obj) {
        if(obj == this) return true;

        if(obj instanceof DestinationAlias){
            final DestinationAlias otherAlias = (DestinationAlias) obj;
            return Objects.equal(getAlias().toUpperCase(), otherAlias.getAlias().toUpperCase())
                    && Objects.equal(getMainCity(), otherAlias.getMainCity());
        }
        return false;
    }
}
这是测试用例:

@Test
public void testEqualsto(){
    Destination dest = new Destination("abc", 1.0f, 1.0f);
    dest.getAliases().add(new DestinationAlias("abc alias", dest));

    Destination dest1 = new Destination("abc", 1.0f, 1.0f);
    dest1.getAliases().add(new DestinationAlias("abc alias", dest1));

    assertEquals(dest, dest1);
}
正如所料,stackoverflow会发生,因为每个equals()依次调用另一个equals(),并发生一个循环


为双向实体重写equals()的推荐方法是什么。

我们必须手动解除冲突。在
DestinationAlias
中,我将更改
equals
表达式,以便它只比较destinationid(它们应该是唯一的):

进一步阅读


但是,我使用destinationID来唯一标识目的地,方法是将其映射到数据库上的主键。(代理对象可能为空)理想情况下,在给定的工作单元中,您应该只有一个具有相同ID的实体实例。如果(obj==this)快捷方式,则可以使用
快捷方式,无限递归表示违反了此约束。@请详细说明一下该语句,好吗?ORMs的作用是,当您多次加载具有相同键的实体时,始终会返回相同的对象。有两个代表同一数据库记录的
Destination
对象是我宁愿避免的事情,而不是试图支持它。如果您在应用程序中确保不会发生这种情况,那么您的原始代码就不会无限递归。
return Objects.equal(getAlias().toUpperCase(), otherAlias.getAlias().toUpperCase())
            && Objects.equal(getMainCity().getId(), otherAlias.getMainCity().getId());
                                          ^^^^^^^^                          ^^^^^^^^