在我的代码中,我有一些地图。然后我有一个类似下面的方法,它采用其中一个映射,按条件对值进行排序,并返回顶部列表,并带有参数给定的数量。
示例:
如果输入地图是
我在参数中用 quantity = 2 调用方法,我给出了2个最高映射条目的列表,逐渐排序
现在,我为每张地图都有一个这样的方法,它们只有不同之处:
<Type1, Type2>
声明和(distances.entrySet());
人口。我能否以某种方式推广这个方法,只能使用一种相似的方法,能够接收任何类型的东西吗?
private static Map<String, Double> distances = new TreeMap<>();
private static Map<String, Integer> titles = new TreeMap<>();
private static Map<Integer, Integer> hours = new TreeMap<>();
private static Map<Date, Integer> days = new TreeMap<>();
public static List<Entry<String, Double>> getTopDistances(int quantity) {
List<Map.Entry<String, Double>> all = new ArrayList<>(distances.entrySet());
List<Map.Entry<String, Double>> requested = new ArrayList<>();
Collections.sort(all, new Comparator<Map.Entry<String, Double>>() {
@Override
public int compare(Entry<String, Double> e1, Entry<String, Double> e2) {
return (e2.getValue().compareTo(e1.getValue()));
}
});
int i = 0;
while (all.iterator().hasNext() && ++i <= quantity) {
requested.add(all.get(i - 1));
}
return requested;
}
我可以肯定继续分离所有方法,但我感觉更好的方法。已经研究过泛型,通配符,集合和接口,我认为这是可行的方法,但我仍然需要推动。
答案 0 :(得分:2)
使用Java Streams,一行可以将您想要的内容从地图生成到最终列表。贝娄我把它打包成一个私密的方法,它更整洁,但如果你愿意,你可以内联它。
由于您的所有值均为Comparable
:
private <K, V extends Comparable<V>> List<Map.Entry<K,V>> getTop(Map<K,V> map, int quantity) {
return map.entrySet().stream()
.sorted((a,b) -> b.getValue().compareTo(a.getValue()))
.limit(quantity)
.collect(Collectors.toList());
}
如果值类型不具有可比性,则需要将比较器作为附加参数传递:
private <K, V> List<Map.Entry<K,V>> getTop(Map<K,V> map, Comparator<V> cmp, int quantity) {
return map.entrySet().stream()
.sorted((a,b) -> cmp.compare(b,a))
.limit(quantity)
.collect(Collectors.toList());
}
答案 1 :(得分:1)
你不能创建比较器来比较两个不同类型的可比对象,所以你必须这样做:
private static Map<String, Double> distances = new TreeMap<>();
private static Map<String, Integer> titles = new TreeMap<>();
private static Map<Integer, Integer> hours = new TreeMap<>();
private static Map<Date, Integer> days = new TreeMap<>();
public static List<Map.Entry<String, Double>> getTopDistances(int quantity) {
List<Map.Entry<String, Double>> all = new ArrayList<>(distances.entrySet());
List<Map.Entry<String, Double>> requested = new ArrayList<>();
all.sort(naturalOrder());
int i = 0;
while (all.iterator().hasNext() && ++i <= quantity) {
requested.add(all.get(i - 1));
}
return requested;
}
public static <T extends Comparable<? super T>> Comparator<Map.Entry<?,T> naturalOrder() {
return (e1, e2) -> e2.getValue().compareTo(e2.getValue());
}