我在 aLinkedHashSet
中有一个实现equals
, hashCode
and的对象compareTo
(在超类中),但是当我尝试从集合中删除该确切对象时,set.remove(obj)
remove 方法返回false
并且该对象保留在集合中。是否LinkedHashSet
应该调用equals()
其对象的方法?因为它没有。这可能是一个java错误吗?我正在运行 1.6.0_25。
问问题
2474 次
3 回答
5
我的猜测是您的对象的hashCode()
实现返回的值与您将对象添加到集合时的值不同。
于 2011-10-26T02:13:36.093 回答
0
LinkedHashSet
对我来说很好:
import java.util.*;
public class Test {
public static void main( String[] args ) {
LinkedHashSet<String> lhs = new LinkedHashSet<String>();
String s = "hi";
lhs.add( s );
System.out.println( lhs );
lhs.remove( s );
System.out.println( lhs );
}
}
也许您正在向 remove 方法传递对不同对象的引用?您确定您没有以任何方式更改参考吗?
还要确保hashCode()
在插入时返回与尝试删除时相同的值。
于 2011-10-26T02:12:32.127 回答
0
这是一个错误的机会LinkedHashSet
非常小。您应该将此视为对您的问题的合理解释。
假设这是您的代码中的一个错误,那么它可能是由于许多原因造成的。例如:
- 您的
equals
和hashCode
方法正在为该对象返回矛盾的答案。 - 您的
equals
orhashCode
方法依赖于可变字段,并且当对象在集合中时,这些字段正在更改。(例如,如果 hashcode 值发生变化,对象很可能在错误的 hash 链上,导致remove
方法找不到它。) - 您已将该
equals
方法声明为重载,而不是equals(Object)
. (这可以解释为什么你equals
没有被调用......假设你的断言实际上是正确的。) - 您要删除的对象(实际上)不是您插入的对象。
- 其他东西已经移除了该对象。
- 您正在运行与您正在检查的源代码不匹配的某个类的不同版本。
现在,我知道您已经驳回了其中一些解释。但这可能为时过早。审查您基于该解雇的证据。
您可以使用的另一种方法是使用 Java 调试器来取证检查数据结构(例如 的内部结构LinkedHashSet
)并单步执行应该发生删除的代码。
于 2011-10-26T02:32:03.357 回答