Java 使用树映射和比较器按值排序HashMap
我使用下面的代码创建一个hashmap,然后使用树映射和比较器对hashmap中的值进行排序。然而,结果却出乎意料。 所以任何关于我做错了什么的想法都会有帮助 代码 并且输出的形式是Java 使用树映射和比较器按值排序HashMap,java,sorting,collections,hashmap,Java,Sorting,Collections,Hashmap,我使用下面的代码创建一个hashmap,然后使用树映射和比较器对hashmap中的值进行排序。然而,结果却出乎意料。 所以任何关于我做错了什么的想法都会有帮助 代码 并且输出的形式是 me-2 hello-3 i-3 请检查JavaDoc:您没有返回较大的值,但是对于o1o2,0对于o1=o2和1对于o1o2。所以你可以写: @Override public int compare(Object o1, Object o2) { return ((Integer) map.get(o1
me-2
hello-3
i-3
请检查JavaDoc:您没有返回较大的值,但是对于
o1
o2
,0
对于o1
=o2
和1
对于o1
o2
。所以你可以写:
@Override
public int compare(Object o1, Object o2) {
return ((Integer) map.get(o1)).compareTo((Integer) map.get(o2);
}
请检查JavaDoc:您没有返回较大的值,但是对于
o1
o2
,0
对于o1
=o2
和1
对于o1
o2
。所以你可以写:
@Override
public int compare(Object o1, Object o2) {
return ((Integer) map.get(o1)).compareTo((Integer) map.get(o2);
}
TreeMap
的
基于红黑树的NavigableMap实现。地图已排序
根据其键的自然顺序
我们不应该通过使用TreeMap
按值排序来违反此规则
但是,要按值排序,我们可以执行以下操作:
map
Collection.sort
对条目进行排序LinkedHashMap
:保持键按插入顺序插入,当前按自然顺序排序李>
LinkedHashMap
作为排序后的map
返回
public static <K extends Comparable,V extends Comparable> Map<K,V> sortByValues(Map<K,V> map){
List<Map.Entry<K,V>> entries = new LinkedList<Map.Entry<K,V>>(map.entrySet());
Collections.sort(entries, new Comparator<Map.Entry<K,V>>() {
@Override
public int compare(Entry<K, V> o1, Entry<K, V> o2) {
return o1.getValue().compareTo(o2.getValue());
}
});
Map<K,V> sortedMap = new LinkedHashMap<K,V>();
for(Map.Entry<K,V> entry: entries){
sortedMap.put(entry.getKey(), entry.getValue());
}
return sortedMap;
}
}
公共静态映射排序值(映射映射){
列表条目=新的LinkedList(map.entrySet());
Collections.sort(条目,新的Comparator(){
@凌驾
公共整数比较(条目o1、条目o2){
返回o1.getValue().compareTo(o2.getValue());
}
});
Map sortedMap=new LinkedHashMap();
对于(Map.Entry:entries){
sortedMap.put(entry.getKey(),entry.getValue());
}
返回分拣的DMAP;
}
}
树状图
清楚地说明:
基于红黑树的NavigableMap实现。地图已排序
根据其键的自然顺序
我们不应该通过使用TreeMap
按值排序来违反此规则
但是,要按值排序,我们可以执行以下操作:
map
Collection.sort
对条目进行排序LinkedHashMap
:保持键按插入顺序插入,当前按自然顺序排序李>
LinkedHashMap
作为排序后的map
返回
public static <K extends Comparable,V extends Comparable> Map<K,V> sortByValues(Map<K,V> map){
List<Map.Entry<K,V>> entries = new LinkedList<Map.Entry<K,V>>(map.entrySet());
Collections.sort(entries, new Comparator<Map.Entry<K,V>>() {
@Override
public int compare(Entry<K, V> o1, Entry<K, V> o2) {
return o1.getValue().compareTo(o2.getValue());
}
});
Map<K,V> sortedMap = new LinkedHashMap<K,V>();
for(Map.Entry<K,V> entry: entries){
sortedMap.put(entry.getKey(), entry.getValue());
}
return sortedMap;
}
}
公共静态映射排序值(映射映射){
列表条目=新的LinkedList(map.entrySet());
Collections.sort(条目,新的Comparator(){
@凌驾
公共整数比较(条目o1、条目o2){
返回o1.getValue().compareTo(o2.getValue());
}
});
Map sortedMap=new LinkedHashMap();
对于(Map.Entry:entries){
sortedMap.put(entry.getKey(),entry.getValue());
}
返回分拣的DMAP;
}
}
参考:您所做的实际上是对工具的滥用 我相信你需要做的是:
sgn(compare(x,y))==-sgn(compare(y,x))(原始实现更糟糕)
一些代码片段仅用于提供提示:
List<String> words = ....;
Map<String, Integer> wordFrequencyMap = new HashMap<String, Integer>();
// iterate words and update wordFrequencyMap accordingly
List<String> uniqueWords = new ArrayList<String>(new HashSet<String>(words));
Collections.sort(uniqueWords, new WordFrequencyComparator<String>(wordFrequencyMap));
for (String w : uniqueWords) {
System.out.println("word : " + w + " frequency : " + wordFrequencyMap.get(w));
}
列出单词=。。。。;
Map wordFrequencyMap=newhashmap();
//迭代单词并相应地更新wordFrequencyMap
List uniqueWords=newarraylist(newhashset(words));
排序(uniqueWords,newwordfrequencyccomparator(wordFrequencyMap));
for(字符串w:唯一字){
System.out.println(“单词:+w+”频率:+wordFrequencyMap.get(w));
}
缺少的部分应该不会有什么困难。您所做的实际上是对工具的滥用
我相信你需要做的是:
有一个输入单词的列表/数组(通过拆分输入字符串得到它仍然很好)
创建一个映射,将单词存储为关键字,将频率存储为值
收集唯一的单词,然后根据频率对集合进行排序
在进行输出时,遍历已排序的唯一单词列表,对于每个元素,从frequencyMap中获取频率,并输出单词+频率
当然,您仍然可以使用树集之类的东西,并使用频率作为键,但您应该将单词列表作为此映射的值(也称为多映射),而不是编写一个有问题的比较器,它不遵循比较器的契约:您的原始实现和其中一个答案的注释中的实现都不符合所有x和y的sgn(compare(x,y))==-sgn(compare(y,x))(原始实现更糟糕)
一些代码片段仅用于提供提示:
List<String> words = ....;
Map<String, Integer> wordFrequencyMap = new HashMap<String, Integer>();
// iterate words and update wordFrequencyMap accordingly
List<String> uniqueWords = new ArrayList<String>(new HashSet<String>(words));
Collections.sort(uniqueWords, new WordFrequencyComparator<String>(wordFrequencyMap));
for (String w : uniqueWords) {
System.out.println("word : " + w + " frequency : " + wordFrequencyMap.get(w));
}
列出单词=。。。。;
映射字频率映射