Java: HashCode and Equals Contract


In Java java.lang.Object is the superclass of all the classes provides two very important methods :

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

See Also:

Internally these methods are used when need to check equality of objects but developer implementation prospects mainly used when need to implement HashMap because on that time developers have to implement these methods inside your User Defined class. Lot’s of the time when the developer is not aware of the contract of hashcode() and equals() method they make mistake and not received expected results from HashMap. Before going to detail of hashcode() and equals() contract, Let’s discuss first the problems.

Most Common Problem

In this example,  green and red car object is stored successfully in a HashMap, but when the map is asked to retrieve this green car object, the car object is not found in map and returning as null.

import java.util.HashMap;
import java.util.Map;

public class Car {
	private String color;

	public Car(String color) {
		this.color = color;
	}

	public boolean equals(Object obj) {
		if (!(obj instanceof Car))
			return false;
		if (obj == this)
			return true;
		return this.color.equals(((Car) obj).color);
	}
	public static void main(String[] args) {
		Car a1 = new Car("green");//hashcode
		Car a2 = new Car("red");

		// HashMap stores car type and its quantity
		Map m = new HashMap();
		m.put(a1, 10);
		m.put(a2, 20);
		//hashcode diffrent from previos green object consider different object
		System.out.println(m.get(new Car("green")));
	}
}
         

Output

null

The above program prints as null. However, we can check that this car object is stored in the map by inspecting in the debugger:

Java hashCode and Equals Contract

In the above program problem is hashcode() method was not implemented.

Before going to the solution to this problem in detail. We need to understand the equals() and hashcode() method contract.

hashcode() and equals() Method Contract

The contract between equals() and hasCode() is that:

  1.  If two objects are equal, then they must have the same hash code value.
  2.  If two objects have the same hashcode value, they may or may not be equal.

The main idea is Map worked on hashing techniques to find an object faster in comparison to linear search. In this case, because the hashcode() method is no implemented. It will call by default method of object class i.e return different hashcode value for different objects. In this above case both the objects store in HashMap and retrieving will have different hashcode values.

See Also: Java: Hashmap Working

In HashMap, store values in form array of buckets of the object where these array having hashcode value while objects having objects that match with the same hashcode. For example, the Hash Code is like a sequence of boxes for storage where different kinds of stuff can be stored in different boxes. It is more efficient if you organize stuff to a different place instead of the same garage. So it’s a good practice to keep kinds of stuff on related boxes i.e equally distribute the hashCode value.

The solution is to add hashCode() method to the Car class. Here we are getting hash value based on the size of color length as implemented below.

import java.util.HashMap;
import java.util.Map;

public class Car {
	private String color;

	public Car(String color) {
		this.color = color;
	}

	public boolean equals(Object obj) {
		if (!(obj instanceof Car))
			return false;
		if (obj == this)
			return true;
		return this.color.equals(((Car) obj).color);
	}

	public int hashCode(){
		return this.color.length();
}
	public static void main(String[] args) {
		Car a1 = new Car("green");//hashcode
		Car a2 = new Car("red");

		// HashMap stores car type and its quantity
		Map m = new HashMap();
		m.put(a1, 10);
		m.put(a2, 20);
		//hashcode different from previous green object consider different object
		System.out.println(m.get(new Car("green")));
	}

}

Output

10
Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s