Today I was doing some pathfinding when I had to use contains()
to find if a class Coord
was in an other keySet()
of Coord
.
I found that when I used to premade method containsKey()
, it was simply not working as I wanted. I made a test to find out what is happening and here it is:
HashMap<Coord, Coord> test = new HashMap<Coord, Coord>();
test.put(new Coord(3, 3), new Coord(0, 0));
System.out.println("HashMap test for containsKey : " + test.containsKey(new Coord(3, 3)));
boolean containsKey = false;
for(Coord a : test.keySet())
{
if(a.equals(new Coord(3, 3)))
{
containsKey = true;
}
}
System.out.println("My test for containsKey : "+containsKey);
And surprisingly, here is what I found :
HashMap test for containsKey : false
My test for containsKey : true
I just wanted to know what is happening and why.
Also, here is the Coord
class :
public class Coord
{
public float x, y;
public Coord(float a, float b)
{
this.x = a;
this.y = b;
}
@Override
public boolean equals(Object b)
{
if(b instanceof Coord)
{
Coord casted = (Coord) b;
return casted.x == x && casted.y == y;
}
return false;
}
}
HashMap
s find objects by their hash code. Part of the contract is that the key class must override hashCode()
as well as equals()
. The default hash codes for separate objects aren't equal, so the object isn't found by get
. In contrast, when you loop over all entries, the hash code isn't used, so only equals
is called, and the object is found.
To find it using get
, override hashCode
in Coord
.
It is always good to override hashCode
whenever you override equals
, and vice versa.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With