如何根据值对TreeMap中的键进行排名?

时间:2015-03-06 19:32:19

标签: java sorting arraylist treemap

我有一个Treemap实现,它将字符串作为键,将整数作为其值。

//YearWord is an TreeMap<String, Integer> implementation
YearWord yr = new YearWord();
yr.put("terminal", 95);        
yr.put("aggregate", 340);
yr.put("catalyst", 181); 

如果我想编写一个函数rank,它接受一个String字并返回一个与该关键字的rank相对应的int值,我该如何处理?我尝试使用arrayLists但它们有点慢。谢谢!

我的方法签名是

public int rank(String word) {
    ????
}

1 个答案:

答案 0 :(得分:3)

你可以尝试这样的事情。如果两个或多个值相关联,则按键排序。

public final class RankableMap<K extends Comparable<K>, V extends Comparable<V>> extends TreeMap<K, V> {

    private static final class Pair<K extends Comparable<K>, V extends Comparable<V>> implements Comparable<Pair<K, V>> {
        private final K k;
        private final V v;
        private Pair(K k, V v) {
            this.k = k;
            this.v = v;
        }
        @Override
        public int compareTo(Pair<K, V> that) {
            int a = v.compareTo(that.v);
            return a != 0 ? a : k.compareTo(that.k);
        }
    }

    private final SortedSet<Pair<K, V>> set = new TreeSet<>();

    @Override
    public V put(K k, V v) {
        V v2 = super.put(k, v);
        if (v.equals(v2))
            return v2;
        if (v2 != null)
            set.remove(new Pair<>(k, v2));
        set.add(new Pair<>(k, v));
        return v2;
    }

    @Override
    public V remove(Object k) {
        V v = super.remove(k);
        if (v != null)
            set.remove(new Pair<>((K) k, v));
        return v;
    }

    @Override
    public void clear() {
        super.clear();
        set.clear();
    }

    public int rank(K k) {
        return 1 + set.headSet(new Pair<K, V>(k, get(k))).size();
    }
}

我使用以下代码测试了这个类

RankableMap<String, Integer> map = new RankableMap<>();
map.put("quayside", 95);
map.put("surrogate", 340)   
map.put("merchantman", 181);
map.put("foo", 340);
map.put("bar", 42);
for (String key : map.keySet())
    System.out.println(key + " rank = " + map.rank(key));
map.remove("bar");
System.out.println();     
for (String key : map.keySet())
    System.out.println(key + " rank = " + map.rank(key));

它给出了以下结果:

bar rank = 1
foo rank = 4
merchantman rank = 3
quayside rank = 2
surrogate rank = 5

foo rank = 3
merchantman rank = 2
quayside rank = 1
surrogate rank = 4