Rohit Pandey
Rohit Pandey

Reputation: 2681

Best way to hash multiple keys in java

I have a set of four numbers and they together make up a key. So, a unique combination of them should correspond lead to one value. What is the best way to prepare a hashmap for this purpose. The options are -

1) Make a unique key through concatenating them into a string 2) Make a unique key through adding them up (multiplying some of them with powers of 10 to avoid duplication). 3) Make a class that has the four numbers as fields and hash an instance of the class.

And if it is the third, I can't figure out how to implement this approach (assuming it is possible). The code below should print 2, but prints nothing.

 AdjFactor a = new AdjFactor(2,3,4,5);
    AdjFactor b = new AdjFactor(3,3,4,5);
    HashMap<AdjFactor,Double> factrs = new HashMap<>();
    factrs.put(a, 1d);
    factrs.put(b, 2d);
    AdjFactor c = new AdjFactor(1,3,4,5);
    AdjFactor d = new AdjFactor(3,3,4,5);
    if(factrs.containsKey(c)){
        System.out.println(factrs.get(c));
    }
    if(factrs.containsKey(d)){
        System.out.println(factrs.get(d));
    }

Here is my AdjFactor class -

public class AdjFactor {
public int demo;
public int month;
public int year;
public int site;

AdjFactor(int demo1,int month1,int year1,int site1){
    this.demo = demo1;
    this.month = month1;
    this.year = year1;
    this.site = site1;
 }
public boolean equals(AdjFactor a, AdjFactor b){
    if(a.demo==b.demo && a.month==b.month && a.year==b.year && a.site==b.site)return true;
    else return false;
}
}

Upvotes: 1

Views: 281

Answers (2)

fge
fge

Reputation: 121710

The code below should print 2, but prints nothing.

This is because your AdjFactor class does not implement .equals() and .hashCode()...

As a result, it uses Object's defaults; and an Object .equals() another one if and only if they are exactly the same references!

==> implement .equals() and .hashCode() for your class

Obligatory, Javadoc, links for you to read. If you use Java 7, look at the Objects class which can help you.

EDIT sample implementation:

public class AdjFactor 
{
    // ....
    @Override
    public int hashCode()
    {
        return demo ^ month ^ year ^ site;
    }

    @Override
    public boolean equals(final Object obj)
    {
        if (this == obj)
            return true;
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        final AdjFactor other = (AdjFactor) obj;
        return demo == other.demo
            && month == other.month
            && year == other.year
            && site == other.site;
    }
}

Upvotes: 2

renke
renke

Reputation: 1230

And regarding the hashcode question, you will be ok with

Arrays.hashCode(new int[] { demo, month, year, site });

Upvotes: 1

Related Questions