Error handling 尝试在optaplannercode的实体上添加哈希代码时出错

Error handling 尝试在optaplannercode的实体上添加哈希代码时出错,error-handling,drools,equals,hashcode,optaplanner,Error Handling,Drools,Equals,Hashcode,Optaplanner,我在optaplanner上的一个项目中练习,我试图在我的实体上添加equals和hashcode。首先,我添加了equals方法,效果非常好!在那之后,我添加了散列码,结果出错了 @Override public boolean equals(Object o) { if (this == o) { return true; } else if (o instanceof CloudBus) { CloudBus otherBus = (CloudBus

我在optaplanner上的一个项目中练习,我试图在我的实体上添加equals和hashcode。首先,我添加了equals方法,效果非常好!在那之后,我添加了散列码,结果出错了

@Override
public boolean equals(Object o) {
if (this == o) {
        return true;
    } else if (o instanceof CloudBus) {
        CloudBus otherBus = (CloudBus) o;
        return (capacity == otherBus.getCapacity());
    } else {
        return false;
    }
}

@Override
public int hashCode() {
    return new HashCodeBuilder()
            .append(capacity)
            .toHashCode();
}
错误:
严重:路径为[/WebApp]的上下文中Servlet[WebApp]的Servlet.service()引发异常[com.WebApp.jersey中规则“conflictingStartBusTooSmall”的异常执行结果:java.lang.IllegalStateException:constraintMatchTotal(com.WebApp.jersey/conflictingStartBusTooSmall=-97hard/0medium/0soft)无法添加constraintMatch(com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83435,CloudBus-17]=-1hard/0medium/0soft)到其约束技术集([com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83555,CloudBus-3]=-22hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83580,CloudBus-3]=-4hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83594,CloudBus-3]=-8hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83753,CloudBus-3]=-1hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83479,CloudBus-4]=-6hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83435,CloudBus-6]=-1hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83429,CloudBus-8]=-26hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83610,CloudBus-8]=-17hard/0medium/0soft,com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83403,CloudBus-10]=-11hard/0medium/0soft])与根本原因相关,我认为您需要在CloudBus的
equals()和
hashCode()中包含另一个属性
这将在具有相同容量的两个不同的CloudBus之间产生差异。一个好的候选者是总线的ID。由于ID是唯一的,所以在
equals()
hashCode()
中包含其他属性没有多大意义(两个不同的总线将始终不相等,无论它们是否具有相同的容量等)

仅基于容量进行比较的问题在于,两条不同的总线可以相等(并且具有相同的哈希代码)。因此,您将有两个相同的不同约束匹配,因此后者不能添加到
ConstraintMatchTotal
constraintMatchSet
,因为“相等”约束匹配已在其中。请参阅。当提供更好的格式时,从异常消息中可以明显看出这一点:

ERROR: SEVERE: Servlet.service() for servlet [WebApp] in context with path [/WebApp] threw exception [
Exception executing consequence for rule "conflictingStartBusTooSmall" in com.webapp.jersey: java.lang.IllegalStateException:
  The constraintMatchTotal (com.webapp.jersey/conflictingStartBusTooSmall=-97hard/0medium/0soft)
  could not add constraintMatch (com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83435, CloudBus-17]=-1hard/0medium/0soft)
  to its constraintMatchSet ([
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83555, CloudBus-3]=-22hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83580, CloudBus-3]=-4hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83594, CloudBus-3]=-8hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83753, CloudBus-3]=-1hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83479, CloudBus-4]=-6hard/0medium/0soft,
--> com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83435, CloudBus-6]=-1hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83429, CloudBus-8]=-26hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83610, CloudBus-8]=-17hard/0medium/0soft,
    com.webapp.jersey/conflictingStartBusTooSmall/[CloudRoute-83403, CloudBus-10]=-11hard/0medium/0soft
  ]).
] with root cause

假设所有总线具有相同的容量,高亮显示的约束匹配与将要插入的约束匹配具有相同的哈希代码,因为两者都具有相同的CloudRoute和具有相同容量的总线。

因此更改默认对象相等性不能仅断开实体禁忌搜索(不是默认的算法,所以只有很低比例的用户使用它),还有“解释分数”API(ConstraintMatchTotal/Commission),迟早每个人都会使用它。这很有趣!我怀疑我们没有看到这种情况发生更多的原因是,只要同一解决方案中的两个不同实体不被视为相等,就可以了。