具有自定义相等条件的 Java HashSet?

2022-08-31 20:39:56

我正在寻找类似于Java TreeSet在实例化时接收自定义比较器的能力,因此我不需要使用对象的默认相等(和哈希代码)标准。

我能想到的最接近的是将我的对象包装在一个私有的自定义类中,但这似乎很棘手:(这最终成为编程时反复出现的主题,所以我想知道是否有一些东西已经可供我们使用。也许在公共图书馆?

谢谢


答案 1

不,您已经找到了应该使用的解决方案。

即使对于 ,也不愿意使用与以下各项不兼容的比较标准:TreeSetequals

请注意,如果排序集要正确实现 Set 接口,则由排序集(无论是否提供显式比较器)维护的排序必须与 equals 一致。

我不知道Apache Commons,但Guava特别拒绝了这种事情的请求,尽管你可以使用Guava Equivalence实现你想要的东西:

Equivalence<T> equivalence = new Equivalence<T>() {
    @Override
    protected boolean doEquivalent(T a, T b) {
        return CustomComparator.equals(a, b);
    }

    @Override
    protected int doHash(T item) {
        return CustomHashCodeGenerator.hashCode(item);
    }
};
List<T> items = getItems();
Set<Equivalence.Wrapper<T>> setWithWrappedObjects = items.stream()
    .map(item -> equivalence.wrap(item))
    .collect(Collectors.toSet());

答案 2

有几个第三方集合框架允许自定义相等逻辑。这非常适合覆盖无法更改源的对象的相等性。

Trove 的映射/集支持使用自定义哈希策略,允许您根据输入数据的特征调整集合。此功能还允许您在无法覆盖 Object.hashCode() 时定义哈希函数。

为了实现这一点,任何需要标准校正的类型都必须实现HE-Collection接口EqualsAndHashCorrection。此接口定义了 hashCodeInHeCollection() 和 equalsInHeCollection(Object) 的方法,它们用于更正不正确的实现方法 hashCode() 和 equals(Object)。


推荐