Java hashCode有疑问

我有这个程序:
import java.util.*;
public class test {
    private String s;
    public test(String s) { this.s = s; }
    public static void main(String[] args) {
        HashSet<Object> hs = new HashSet<Object>();
        test ws1 = new test("foo");
        test ws2 = new test("foo");
        String s1 = new String("foo");
        String s2 = new String("foo");
        hs.add(ws1); 
        hs.add(ws2); 
        hs.add(s1); 
        hs.add(s2); // removing this line also gives same output.
        System.out.println(hs.size()); 
    } 
}
请注意,这不是作业。我们今天早些时候在测验中被问到了这个问题。我知道答案,但试图理解为什么会这样。 上面的程序给出3作为输出。 任何人都可以解释为什么会这样吗? 我想(不确定):
java.lang.String
类覆盖
java.lang.Object
hashCode
方法。所以具有值“foo”的
String
对象将被视为重复。测试类不会覆盖
hashCode
方法并最终使用
java.lang.Object
版本,并且此版本始终为每个对象返回不同的哈希码,因此添加的两个测试对象将被视为不同。     
已邀请:
在这种情况下,它不是
hashCode()
,而是
equals()
方法。 HashSet仍然是Set,其语义不允许重复。使用
equals()
方法检查重复项,如果是String,则返回
true
但是对于你的
test
equals()
方法没有定义,它将使用
Object
的默认实现,只有当两个引用都是同一个实例时才会返回true。 方法
hashCode()
不用于检查对象是否应该被视为相同,而是用于基于散列函数将它们分布在集合中的方法。绝对有可能对于两个对象,此方法将返回相同的值,而
equals()
将返回false。 附:
hashCode
ѭѭ的实施并不保证价值的唯一性。使用简单的循环检查很容易。     
Hashcode用于缩小搜索结果范围。当我们首先尝试在
HashMap
中插入任何键时,它会检查是否有任何其他对象存在相同的哈希码,如果是,则检查
equals()
方法。如果两个对象相同,那么
HashMap
将不会添加该键,而是用新值替换旧值。     
事实上,它不是覆盖
hashcode()
,它是关于
equals
方法。设置不允许重复。副本是对象在逻辑上相等的副本。 为了验证您可以尝试
System.out.println(ws1.equals(ws2));
System.out.println(s1.equals(s2));
如果对象相等,则一组只接受一个。     
下面是几个(很多很多)子弹从我准备到SCJP的平等和哈希码。 希望能帮助到你: equals(),hashCode()和toString()是公共的。 覆盖toString(),以便System.out.println()或其他方法可以看到有用的东西,比如对象的状态。 使用==确定两个引用变量是否引用同一个对象。 使用equals()确定两个对象是否有意义等效。 如果不重写equals(),则对象将不是有用的散列键。 如果不重写equals(),则不能将不同的对象视为相等。 字符串和包装器重写equals()并制作好的哈希键。 覆盖equals()时,请使用instanceof运算符以确保您正在评估适当的类。 覆盖equals()时,比较对象的重要属性。 equals()合同的重点:       一个。反身:x.equals(x)为真。    湾对称:如果x.equals(y)为真,则y.equals(x)必须为真。    C。传递:如果x.equals(y)为真,并且y.equals(z)为真,则z.equals(x)为真。    d。一致:多次调用x.equals(y)将返回相同的结果。     即Null:如果x不为null,则x.equals(null)为false。    F。如果x.equals(y)为true,则x.hashCode()== y.hashCode()为true。 如果重写equals(),则覆盖hashCode()。 HashMap,HashSet,Hashtable,LinkedHashMap,&amp; LinkedHashSet使用散列。 一个合适的hashCode()覆盖符合hashCode()契约。 有效的hashCode()覆盖在其桶之间均匀分配密钥。 重写的equals()必须至少与其hashCode()配合一样精确。 重申一下:如果两个对象相等,则它们的哈希码必须相等。 hashCode()方法为所有实例返回相同的值是合法的(尽管在实践中它的效率非常低)。 此外,如果您实现equals和hashcode,则必须正确处理瞬态字段(如果有)。 Commons对EqualsBuilder和HashcodeBuilder有很好的实现。它们在Coomons Lang有售 http://commons.apache.org/lang/ 我使用它们whenevr我需要实现equals和hashcode。     

要回复问题请先登录注册