【发布时间】:2012-04-08 04:11:11
【问题描述】:
由于数组中的equals函数只检查实例,所以它不能很好地与Set一起使用。 因此,我想知道如何在 Java 中制作一组数组?
一种可能的方法是将每个数组放在一个对象中,并为该类实现 equals 函数,但这会不会过多地降低性能?
【问题讨论】:
由于数组中的equals函数只检查实例,所以它不能很好地与Set一起使用。 因此,我想知道如何在 Java 中制作一组数组?
一种可能的方法是将每个数组放在一个对象中,并为该类实现 equals 函数,但这会不会过多地降低性能?
【问题讨论】:
不要使用原始数组,除非因为某些遗留 API 需要数组而绝对必须这样做。
请始终尝试使用类型安全的ArrayList<T>,这样您就不会遇到此类问题。
【讨论】:
如果你让你的 Set 成为 TreeSet 的一个实例,你可以指定一个自定义的 Comparator,它将用于所有的比较(甚至相等)。
【讨论】:
您可以为您的数组创建一个包装类并相应地覆盖哈希码和等于。 例如:
public class MyArrayContainer {
int[] myArray = new int[100];
@Override
public boolean equals(Object other) {
if (null != other && other instanceof MyArrayContainer) {
MyArrayContainer o = (MyArrayContainer) other;
final int myLength = myArray.length;
if (o.myArray.length != myLength) {
return false;
}
for (int i = 0; i < myLength; i++) {
if (myArray[i] != o.myArray[i]) {
return false;
}
}
return true;
}
return false;
}
@Override
public int hashCode() {
return myArray.length;
}
}
【讨论】:
从Java 9 开始,您可以使用Arrays::compare 方法作为TreeSet 的比较器,用于比较数组的内容。
Set<String[]> set = new TreeSet<>(Arrays::compare);
String[] val1 = {"one", "two"};
String[] val2 = {"one", "two"};
String[] val3 = {"one", "two"};
set.add(val1);
set.add(val2);
System.out.println(set.size()); // 1
System.out.println(set.contains(val1)); // true
System.out.println(set.contains(val2)); // true
System.out.println(set.contains(val3)); // true
【讨论】:
由于 ArrayList 类已经包装了一个数组,您可以扩展它并覆盖 equals 和 hashCode 方法。这是一个示例:
public MyArrayList extends ArrayList<MyClass> {
@Override
public boolean equals(Object o) {
if (o instanceof MyArrayList) {
//place your comparison logic here
return true;
}
return false;
}
@Override
public int hashCode() {
//just a sample, you can place your own code
return super.hashCode();
}
}
更新:
您甚至可以覆盖它以用于一般用途,只需将代码更改为:
public MyArrayList<T> extends ArrayList<T> {
//overrides the methods you need
@Override
public boolean equals(Object o) {
if (o instanceof MyArrayList) {
//place your comparison logic here
return true;
}
return false;
}
}
【讨论】:
扩展 Set 并覆盖 equals 方法的类可以做到这一点。
【讨论】: