package com.wang.testMianShi;
public class Person {
private String name;
private int age;
public Person() {
super();
}
public Person(String name, int age) {
super();
this.name = name;
this.age = age;
}
//测试hashCode
// @Override
// public boolean equals(Object obj) {
// // TODO Auto-generated method stub
// return true;
// }
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@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;
}
/* (non-Javadoc)
* @see java.lang.Object#equals(java.lang.Object)
*/
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Person other = (Person) 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 String toString() {
// return "Person [name=" + name + ", age=" + age + "]";
// }
}
package com.wang.testMianShi;
import java.util.HashMap;
import java.util.Map;
public class testHashMap {
public static void main(String[] args) {
//
Person p1 = new Person("tom", 18);
Person p2 = new Person("jack", 19);
Map hMap5 = new HashMap<>();
hMap5.put(p1, "1111");
hMap5.put(p2, "2222");
System.out.println(hMap5 +"--"+ hMap5.size()); //2
p1.setAge(5);
System.out.println(hMap5);
hMap5.put(p1, "333");
System.out.println(hMap5);
System.out.println(hMap5.get(p1));
}
}
奇葩的是竟然允许key重复,而且引用地址相同,都是com.wang.testMianShi.Person@1c5ae
{com.wang.testMianShi.Person@31aded=2222, com.wang.testMianShi.Person@1c741=1111}–2
{com.wang.testMianShi.Person@31aded=2222, com.wang.testMianShi.Person@1c5ae=1111}
{com.wang.testMianShi.Person@1c5ae=333, com.wang.testMianShi.Person@31aded=2222, com.wang.testMianShi.Person@1c5ae=1111}
推荐你看下Map的原理
map在存放值的时候不是用的对象的地址,而是用的对象的hashcode
你先将p1作为key放进map,
然后更改了p1的值,这时候p1的hashcode已经改变了,再次存放时map以为是不同的key,所以就存进去了。
以下是HashMap.put的内部实现
public V put(K key, V value) {
return putVal(hash(key), key, value, false, true);
}
p1.setAge(5)之后p1的hashCode就改变了,上述函数中hash(key)就发生了变化,虽然key是相同的对象,但是HashMap还是将其作为一个新key存储了。
出于效率的考虑,这种场景就不被支持了。算是是HashMap的一个坑吧。