Pages

Saturday, February 12, 2011

Sorting a HashMap in Java

First of all I have to point out that a HashMap can not be in a "sorted" state. This is because a HashMap does not have an order. On the other hand a TreeMap does have an order (it implements the interface SortedMap). So to sort a HashMap by key, you can use the code below.

Map sortedMap = new TreeMap(yourOriginalMap);

This will sort the map according to the keys' natural order.


In order to sort the HashMap based on the values, we have to pass a Comparator to the constructor of TreeMap. For this example let us assume that the values of the HashMap that you need to sort are Integers. Then the comparator would look like the following.


public class MyComparator implements Comparator<Object> {

    Map theMapToSort;

    public MyComparator(Map theMapToSort) {
        this.theMapToSort = theMapToSort;
    }

    public int compare(Object key1, Object key2) {
        Integer val1 = (Integer) theMapToSort.get(key1);
        Integer val2 = (Integer) theMapToSort.get(key2);
        if (val1 < val2) {
            return -1;
        } else {
            return 1;
        }
    }
}

Then you can sort the map using the following code

MyComparator comp = new MyComparator(originalMap);
TreeMap treeMap = new TreeMap(comp);
treeMap.putAll(originalMap);


Now the treeMap object will contain the values in the orginalMap, sorted by the values.

6 comments:

  1. Nice Program ........buddy

    I hope you would love this program
    http://examplesinjava.blogspot.com/search/label/Unique%20word%20count

    ReplyDelete
    Replies
    1. code looks code but it needs to be udpated to use Generics. Here is an example of How to sort HashMap in Java by keys and values which uses generics

      Delete
  2. Thanks for the main concept! I improved on this by making it generic and null-safe:

    public class MapValueComparator> implements Comparator {
    private Map map;

    public MapValueComparator(Map mapToSort) {
    map = mapToSort;
    }

    @Override
    public int compare(K key1, K key2) {
    V value1 = map.get(key1);
    V value2 = map.get(key2);

    if (value1 == null && value2 == null) {
    return 0; // both null; return equal
    } else if (value1 == null) {
    return -1; // first value null, return less than
    } else if (value2 == null) {
    return 1; // second value null, return greater than
    } else {
    return value1.compareTo(value2);
    }
    }
    }

    ReplyDelete
  3. Sorry, make sure not to return zero (TreeMap will overwrite entries which come back equal comparison).

    ReplyDelete
  4. This doesn't work for same values, the "treeMap" return values to "null"

    ReplyDelete