Java equals() and hashCode() Contract


The Java super class java.lang.Object defines two important methods:

public boolean equals(Object obj)
public int hashCode()

In this post, I will first show an example of a common mistake, and then explain how the equals() and hashCode() contract works.

1. A common mistake

Common mistake is shown in the example below.

import java.util.HashMap;
public class Apple {
	private String color;
	public Apple(String color) {
		this.color = color;
	public boolean equals(Object obj) {
		if(obj==null) return false;
		if (!(obj instanceof Apple))
			return false;	
		if (obj == this)
			return true;
		return this.color.equals(((Apple) obj).color);
	public static void main(String[] args) {
		Apple a1 = new Apple("green");
		Apple a2 = new Apple("red");
		//hashMap stores apple type and its quantity
		HashMap<Apple, Integer> m = new HashMap<Apple, Integer>();
		m.put(a1, 10);
		m.put(a2, 20);
		System.out.println(m.get(new Apple("green")));

In this example, a green apple object is stored successfully in a hashMap, but when the map is asked to retrieve this object, the apple object is not found. The program above prints null. However, we can be sure that the object is stored in the hashMap by inspecting in the debugger:

2. Problem caused by hashCode()

The problem is caused by the un-overridden method "hashCode()". The contract between equals() and hashCode() is:
1) If two objects are equal, then they must have the same hash code.
2) If two objects have the same hash code, they may or may not be equal.

The idea behind a Map is to be able to find an object faster than a linear search. Using hashed keys to locate objects is a two-step process. Internally the Map stores objects as an array of arrays. The index for the first array is the hash code of the key. This locates the second array which is searched linearly by using equals() to determine if the object is found.

The default implementation of hashCode() in Object class returns distinct integers for different objects. Therefore, the second apple created in the last statement has a different hash code.

The hash code is like a sequence of buckets, different stuff can be put into different buckets. It is more efficient if we organize stuff to the different buckets instead of the same bucket. So it's a good practice to equally distribute the hashCode value. (Not the main point here though)

The solution is to add hashCode method to the class. Here I just use the color string's length for demonstration.

public int hashCode(){
	return this.color.hashCode();	
Category >> Common Methods >> Diagram  
If you want someone to read your code, please put the code inside <pre><code> and </code></pre> tags. For example:
String foo = "bar";
  • Partha Pratim Sanyal

    HashMap is not an array of arrays, Its just one array of Entry objects, and Entry consists of a Key, Value pair.

  • ASaraswat

    I think it would be helpfull to add that if you use same object reference as it was stored in map i.e. System.out.println(m.get(a1)); you will see the correct result. This explains that if hashCode is not overridden, a default implementation will be used which is always identical for same object. Having sailed that, you should always override hashCode method if object is going to be used in hash based collection

  • Hassan Rajabi

    Hi every one …

    Excuse me ,I am of a question , but I don’t know what is it it’s subject to ask..

    I wanna know that when the System.currentTimeMillis() in java will became zero , I mean when it will start again ?

  • Morten Christensen

    I find it tedious to implement equals() and hashCode() by hand. I also see too many mistakes in code in this area. Better to automate this, so I have just released a free open source tool VALJOGen ( which can generate your value classes with setters/getters (*), Object.hashCode, Object.equals, Object.toString, Comparable.compareTo and more from plain java interfaces. The generated output can be automatically updated when you change your interfaces – no need to maintain the generated code. Let me know what you think?

  • Ashish Thakran

    HashMap works on the principle of hashing. In order to understand the working of HashMap one has to understand hashing.

    Below link can be useful to find out the working of HashMap

    How HashMap works in Java

  • Franco

    You’re welcome. Thanks for the many interesting articles published; I found them very instructive!

  • ryanlr

    Right. It is corrected. Thanks!

  • Franco

    Hi, I’m learning Java and I’m trying to figure out the comparison of the equals method:
    return this.color == ((Apple) obj).color;

    you are comparing two strings with the == operator; don’t you have to use the equals method of the strings? Thank you

  • aly

    Nice one. Thanks for sharing. I will also for more examples and scenarios. Cheers,

  • Good explanation. I think the readers should read too to get a complete picture as both the articles are complimentary

  • Chakradhar

    If you execute the code without the hasCode implementation, it won’t even call the equals method. It will check the equals only when you are comparing the objects (using comparator or comparable…) or in the case, when the hashCode is implemented.