参考连接:http://www.cnblogs.com/shenliang123/archive/2012/04/16/2452206.html html
先查看Java String 的源码java
private final char value[]; private int hash; // Default to 0
equals方法数组
public boolean equals(Object anObject) { if (this == anObject) { return true; } if (anObject instanceof String) { String anotherString = (String)anObject; int n = value.length; if (n == anotherString.value.length) { char v1[] = value; char v2[] = anotherString.value; int i = 0; while (n-- != 0) { if (v1[i] != v2[i]) return false; i++; } return true; } } return false; }
hashCode方法 ide
/** * Returns a hash code for this string. The hash code for a * {@code String} object is computed as * <blockquote><pre> * s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1] * </pre></blockquote> * using {@code int} arithmetic, where {@code s[i]} is the * <i>i</i>th character of the string, {@code n} is the length of * the string, and {@code ^} indicates exponentiation. * (The hash value of the empty string is zero.) * * @return a hash code value for this object. */ public int hashCode() { int h = hash; if (h == 0 && value.length > 0) { char val[] = value; for (int i = 0; i < value.length; i++) { h = 31 * h + val[i]; } hash = h; } return h; }
计算字符串的hashCode是根据对应字符的ASCII来计算的。测试
例如字符串:“123”this
数字 | ASCII 值 |
1 | 49 |
2 | 50 |
3 | 51 |
计算公式:49*31^2+50*31+51=48690spa
为何须要重写equals方法的同时也重写hashCode方法,由于只重写了equals方法但不重写hashCode两个对象相同,但它们的hashCode值不同,这样将它们放在set集合里,他们是不一样的对象,它们的hashCode值不同。code
其次,为何重写equals方法必须重写hashCode方法,由于这两个方法是有关联的。就像上面的例子都用到了value[]数组。htm
Object中的equals是比较的值是否相同,用“==”来比较对象
public boolean equals(Object obj) { return (this == obj); }
测试代码:
package com.example.demo; public class Person { private Integer id; private String username; private Integer age; public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public Integer getAge() { return age; } public void setAge(Integer age) { this.age = age; } public Person(Integer id, String username, Integer age) { this.id = id; this.username = username; this.age = age; } public int hashCode() { final int prime = 31; int result =1; result = prime * 31 + ((id == null) ? 0 : id.hashCode()); return result; } public boolean equals(Object obj) { if(this == obj) { return true; } if(obj == null) { return false; } if(obj instanceof Person) { Person person = (Person) obj; if(id == person.getId() && username.equals(person.getUsername()) && age == person.getAge()) { return true; } return false; } return false; } @Override public String toString() { return "Person [id=" + id + ", username=" + username + ", age=" + age + "]"; }
测试运行:
Person person1 = new Person(1, "Jerry", 28); Person person2 = new Person(1, "Jerry", 27); Set<Person> persons = new HashSet<Person>(); persons.add(person1); persons.add(person2); System.out.println("person1 equals person2: "+person1.equals(person2)); // false System.out.println("persons size:"+persons.size()); // 2 System.out.println("person1 hashCode: "+person1.hashCode()); // 962 System.out.println("person2 hashCode: "+person2.hashCode()); // 962 System.out.println("person1 toString:"+person1.toString()); // person1 toString:Person [id=1, username=Jerry, age=28] System.out.println("person2 toString:"+person2.toString()); // person2 toString:Person [id=1, username=Jerry, age=27] System.out.println(persons); // [Person [id=1, username=Jerry, age=28], Person [id=1, username=Jerry, age=27]] Integer a = 1; System.out.println("1 hashCode: "+ a.hashCode()); // 1 hashCode: 1 String str1 = new String("123"); String str2 = new String("123"); System.out.println(str1 == str2); //false System.out.println(str1.equals(str2)); //true