如何使类在Java中的不同HashMaps中可用

时间:2011-11-01 00:55:02

标签: java hashset

我有一个类属性,它有2个变量,如 int a,b ;

我想在两个不同的HashSet中使用class Attribute。

a 的值相同时,第一个哈希集会将对象视为相等。 但是当 b 的值相同时,第二个哈希集会将对象视为相等。

我知道如果覆盖 等于方法,哈希集将使用equals的覆盖版本来比较两个对象,但在这种情况下我需要两个不同的equals实现()

单向创建属性的两个子类,并为它们提供不同的equals方法,但我想知道是否有更好的这样做的方式,我不必创建属性的子类。

感谢。

6 个答案:

答案 0 :(得分:3)

一种可能的解决方案是不使用HashSet,而是使用TreeSet。它是相同的Set接口,但有一个TreeSet构造函数可以传入Comparator。这样你可以保持Attribute类不变 - 只需创建两个不同的比较器并像

一样使用它
Set<Attribute> setA = new TreeSet<Attribute>(comparatorForA);
Set<Attribute> setB = new TreeSet<Attribute>(comparatorForB);

比较器负责等式检查(例如,如果compare返回0,则对象相等)

答案 1 :(得分:1)

不幸的是,没有“均衡器”类可以覆盖equals逻辑。排序有这样的事情,您可以根据Comparable实现使用自然排序,也可以提供自己的Comparator。我实际上想知道为什么平等检查没有这样的东西。

由于相等的语义是由类定义的,并且可以被认为是该类的特征,因此两个子类方法似乎是最自然的。也许有人知道以一种更简单的方式做到这一点的有用模式,但我从未遇到过它。

编辑:只是想到了某些事情......您可以使用两个Map个实例,例如HashMap,第一个使用a作为关键,第二个使用b作为关键。它可以让你检测到碰撞。然后,您可以将该属性链接到关联的实例。

答案 2 :(得分:1)

我做了一些不同的事情,反而使用 HashSet ,我有使用 HashMap 我在哪里在第一个HashMap中使用 int a 作为键,对象存储为value。 在另一个 HashMap 中,我将键保存为 int b ,将对象保留为值。

这为我提供了对变量 a b 进行哈希处理的方法,因此我不必创建任何子类。

而且,我得到O(1)时间而不是O(log n)。但是我知道我通过使用更多内存来付出代价,但我主要担心的是时间,所以我在TreeSet上选择了HashMap。

感谢大家的意见和建议。

答案 3 :(得分:0)

修改HashMapHashSet以接受散列和相等测试策略非常容易。

public interface Hasher {
    int hashCode(Object o);
}

public interface Equalizer {
    int areEqual(Object o1, Object o2);
}

答案 4 :(得分:0)

一个简单的解决方案是绕过HashSet并直接使用HashMap。首先,使用Attribute属性作为关键字存储每个a,将另一个b存储为{{1}}。

答案 5 :(得分:0)

我可以提出一点hacky但是努力程度较低的解决方案:) 当存储在第二个散列集中时,交换a和b的值,以便通过b的值定义唯一性,然后在从hashset读取类时,再次交换a和b的值以保留原始状态。所以相同的equals / hascode方法将达到目的。