获取哈希映射中的前10个值

8
我正在尝试找出如何从HashMap中获取前10个值。我最初尝试使用TreeMap,并通过值进行排序,然后取前10个值,但似乎这不是选项,因为TreeMap按键排序。我仍想知道哪些键具有最高的值,该映射的K、V是String和Integer。请注意,保留HTML标记。

4
你的意思是“前十名”吗?按照什么标准来确定的? - jsedano
你能否发布一些代码来展示你正在比较哪些元素? - Ian R. O'Brien
TreeMap可以为您进行排序。但是,为了让我们知道您要按什么进行排序,您必须告诉我们! - Kevin
啊对不起,我漏掉了,K,V 都是字符串和整数。我仍然需要知道哪些键具有最高的值。我已经尝试过 TreeMap ,但它只按照规范中定义的键进行排序。 - Tohmas
https://dev59.com/qXVD5IYBdhLWcg3wDG_m - Achintya Jha
7个回答

3
也许你应该为存储在哈希映射中的值对象实现“Comparable”接口。 然后,您可以创建所有值的数组列表:
List<YourValueType> l = new ArrayList<YourValueType>(hashmap.values());
Collection.sort(l);
l = l.subList(0,10);

祝好


相当不错的解决方案。我只需要类似的东西。由于您只提供值,但我还需要键。我进行了轻微修改,并添加了一个比较器以使用条目集。比较器必须按降序比较条目值。List<Entry<String,Integer>> results = new ArrayList<>(hashmap.entrySet());Collections.sort(results, new EntryComparator()); results = results.subList(0, 10); - Sebastian D'Agostino
1
我将其作为另一个答案添加,因为它作为评论看起来很糟糕。 - Sebastian D'Agostino

3
import java.util.Comparator;
import java.util.HashMap;
import java.util.Map;
import java.util.TreeMap;

public class Testing {

    public static void main(String[] args) {

        HashMap<String,Double> map = new HashMap<String,Double>();
        ValueComparator bvc =  new ValueComparator(map);
        TreeMap<String,Double> sorted_map = new TreeMap<String,Double>(bvc);

        map.put("A",99.5);
        map.put("B",67.4);
        map.put("C",67.4);
        map.put("D",67.3);

        System.out.println("unsorted map: "+map);

        sorted_map.putAll(map);

        System.out.println("results: "+sorted_map);
    }
}

class ValueComparator implements Comparator<String> {

    Map<String, Double> base;
    public ValueComparator(Map<String, Double> base) {
        this.base = base;
    }

    // Note: this comparator imposes orderings that are inconsistent with equals.    
    public int compare(String a, String b) {
        if (base.get(a) >= base.get(b)) {
            return -1;
        } else {
            return 1;
        } // returning 0 would merge keys
    }
}

哇,我觉得这可能就是解决方法了,现在要试一下了,谢谢! - Tohmas
@Biswajit,你能解释一下这段代码的复杂度吗?你的代码运行得非常完美,而且方法很简单,我只是想计算一下这段代码的复杂度... - Rushi
@Biswajit,你的代码很棒,但是你如何确保TreeMap的大小始终为10呢?因为你只想要前十个对吧? 每次向TreeMap插入键值对时,您需要检查当前大小是否大于10,如果是,则需要删除TreeMap中最小的键值对。您如何在代码中实现这个最后一部分呢?我没想到人们会在这里回答我的问题,所以我引用了这篇文章并提出了一个新问题Here - Awesome_girl

1
我怕你需要遍历整个映射表。Heap是一种常用的数据结构,用于查找前K个元素,正如本书中所解释的那样。

0
public static void main(String[] args) {
        HashMap<String, Integer> map = new HashMap<String, Integer>();
        // Initialize map
        System.out.println(getTopKeysWithOccurences(map, 10));
}

public static List<Entry<String,Integer>> getTopKeysWithOccurences(Map mp, int top) {
        List<Entry<String,Double>> results = new ArrayList<>(mp.entrySet());
        Collections.sort(results, (e1,e2) -> e2.getValue() - e1.getValue());
        //Ascending order - e1.getValue() - e2.getValue()
        //Descending order - e2.getValue() - e1.getValue()
        return results.subList(0, top);
}

0
如果您正在尝试获取地图中前10个最高的值(假设这些值是数字或至少实现了Comparable接口),请尝试以下方法:
List list = new ArrayList(hashMap.values());
Collections.sort(list);
for(int i=0; i<10; i++) {
   // Deal with your value
}

只有当值类型 Foo 实现了 Comparable<Foo> 接口并且您不使用列表的原始类型时,此代码才能正常工作。 - jlordo
如果OP在他的问题中指定了原始类型,我会使用原始类型 :) - aymeric

0

假设您有一个Map,但此示例适用于任何类型的

Map<String, String> m = yourMethodToGetYourMap();
List<String> c = new ArrayList<String>(m.values());
Collections.sort(c);
for(int i=0 ; i< 10; ++i) {
    System.out.println(i + " rank is " + c.get(i)); 
}

0

我基于sk2212的答案来回答这个问题。

首先,您需要实现一个降序比较器:

class EntryComparator implements Comparator<Entry<String,Integer>> {

    /**
     * Implements descending order.
     */
    @Override
    public int compare(Entry<String, Integer> o1, Entry<String, Integer> o2) {
        if (o1.getValue() < o2.getValue()) {
            return 1;
        } else if (o1.getValue() > o2.getValue()) {
            return -1;
        }
        return 0;
    }

}

然后您可以在类似于以下方法的属性“hashmap”中使用它:

public List<Entry<String,Integer>> getTopKeysWithOccurences(int top) {
    List<Entry<String,Integer>> results = new ArrayList<>(hashmap.entrySet());
    Collections.sort(results, new EntryComparator());
    return results.subList(0, top);
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接