我有一个类和不同的等价规则(equals
和 hashCode
的不同实现)。数据首先在一个进程中生成,其中应用一个等价规则,然后馈送到第二个进程,其中应用另一个等价规则。特别是,我正在做很多 map
操作并且 equals
和 hashCode
被标准库隐式调用(我无法控制).您认为实现这一目标的最佳方法是什么?我现在有两个解决方案:
- 定义两个具有不同
equals
和hashCode
的子类。过程1之后,通过初始化其他子类的对象来进行转换。 - 在类中引入可变状态以指示应用哪个等价规则。
那么你觉得哪个更好或者有没有其他好的方案呢?
最佳答案
可能更优雅的解决方案是自定义 Map
类,它允许自定义散列和相等性评估。
trait MappingScheme[KEY_CLASS,VALUE_CLASS] implements Comparable[VALUE_CLASS] {
def generateHash(key: KEY_CLASS): Int
// Also imposes compare() definition from Comparator
}
class CustomSchemeMap[K,V](mappingScheme: MappingScheme[K,V]) implements Map[K,V] {
// Implement Map methods; use mappingScheme to generate hashes and
// perform equality checks
}
在您的场景中,您将创建两个自定义 MappingScheme
并在您的 CustomSchemeMap
中适本地使用它们。这种方法比您建议的解决方案性能更高(无需创建额外的实例并且您不必改变对象),但它也更合乎逻辑并且更容易遵循。
但是,实现 Map
可能是一项艰巨的任务。如果这似乎遥不可及,我会创建简单的适配器类来环绕您的对象并将它们提供给 map 。
class KeyableAdapter1(o: OriginalClass) {
override def hashCode() = o.hashCode + 10 // e.g.
override def equals(that: Object) = o.stuff == that.stuff // e.g., after cast
def get(): OriginalClass = o // To get it back out, if you need to
}
class KeyableAdapter2(o: OriginalClass) {
override def hashCode() = o.hashCode ^ 10
override def equals(that: Object) = o.otherStuff = that.otherStuff
def get(): OriginalClass = o
}
// Later
myMap.put(new KeyableAdapter1(o1), stuff)
myOtherMap.put(new KeyableAdapter2(o1), moreStuff)
这类似于子类化方法,只是您可以通过 get()
取回原始对象,而且更容易理解(至少在我看来)。
关于java - 在平等规则之间切换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14420561/