class People {
private String name;
private int age; public People(int age, String name) {
super();
this.age = age;
this.name = name;
} @Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
People other = (People) obj;
if (age != other.age)
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
} @Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + age;
result = prime * result + ((name == null) ? 0 : name.hashCode());
return result;
}         public static void main(String[] args) {
People p1 = new People(16, "张三");
People p2 = new People(16, "张三"); System.out.println(p1);
System.out.println(p2);
System.out.println(p1==p2);
}
}==不是比较的是引用地址么,打印出来的地址是一样的,为何p1==p2返回false呢

解决方案 »

  1.   

    跟一下代码就知道了,所谓System.out.println(p1);最终调用代码是
        public String toString() {
    return getClass().getName() + "@" + Integer.toHexString(hashCode());
        }
    而默认情况下hashCode方式是native,jvm会使用内存地址作为hashCode以保证每个对象的唯一性.现在你覆盖了hashCode,在name,age一样的情况下自然hasCode是一样的,但是这个时候hashCode已经和内存地址没关系了.把toString也改写一下就行了. public String toString() {
         return getClass().getName() + "@" + Integer.toHexString(super.hashCode());
        }
      

  2.   

    只是先比较一下地址,如果地址相等自然是同一个对象
    然后再用name的字段的equals方法比较如果名字相等来判断
      

  3.   

    地址真的是一样的吗?
    System.out.println(p1);
    打印的不是P1的地址是打印的应该是p1.tostring()的值.
      

  4.   

    这个已经解释的差不多了。如果你不重写该类的toString()方法。那么System.out.println(p1)。调用的就是他基类的toString()方法。在这里也就是Object的toString()方法。Object的toString()输出格式是 类名+@+16进制的hashcode码。在这里你重写了hashCode()方式。所以就按你的方式而非系统的方式获取hashCode().所以你输出System.out.println(p1) System.out.println(p2).看着是一样的。==确实是比较引用的地址。你想一想,两个对象,在堆内的地址可能一样吗?所以p1==p2 输出false
      

  5.   

    p1,p2分别指向new出来的两个对象。而两个对象肯定是占用两个不同的地址空间。所以无论如何
    p1==p2都是false。System.out.println(p1);
    也就是System.out.println(p1.toString());而p1.toString()是一个字符串。System.out.println(p1==p2);
    可以理解为
    String s1 = p1.toString();
    String s2 = p2.toString();

    s1 == s2,肯定是false。如果随便改改hasCode,和toString方法,就让两个对象占用了一个地址空间,那不是乱了。
    系统中所有对象都占用一个地址,怎么可能出现这种情况呢?