2012-01-24 40 views
3

我想对两个LinkedHashMap的值进行排序。我可以编译它并运行代码,但它告诉我在编译期间使用-Xlint选项,因为它是不安全的代码。它与类型转换的东西有关,但我对如何去做这件事感到非常困惑。我得到这个类,我在班级把inbedded:混淆了如何在另一个类中输入比较器

static class MyComparator implements Comparator { 

     public int compare(Object obj1, Object obj2){ 
      int result=0; 
      Map.Entry e1 = (Map.Entry)obj1 ; 
      Map.Entry e2 = (Map.Entry)obj2 ;//Sort based on values. 

      Integer value1 = (Integer)e1.getValue(); 
      Integer value2 = (Integer)e2.getValue(); 

      if(value1.compareTo(value2)==0){ 

       String word1=(String)e1.getKey(); 
       String word2=(String)e2.getKey(); 

       //Sort String in an alphabetical order 
       result=word1.compareToIgnoreCase(word2); 

      } else { 
       //Sort values in a descending order 
       result=value2.compareTo(value1); 
      } 

      return result; 
     } 

    } 

我试图调用它与我的功能之一:

ArrayList myArrayList=new ArrayList(this.map_freq_by_date.entrySet()); 
Collections.sort(myArrayList, new MyComparator()); 
Iterator itr=myArrayList.iterator(); 

注:this.map_freq_by_date定义如下:

Map<String,Integer> map_freq_by_date = new LinkedHashMap<String,Integer>(); 

我-Xlint选项得到的错误:

unchecked call to ArrayList(java.util.Collection<? extends E>) as a member of the raw type java.util.ArrayList 
ArrayList myArrayList=new ArrayList(this.map_freq_by_date.entrySet()); 


unchecked conversion 
found LogGrep.MyComparator 
required: java.util.Comparator(? super T> 
    Collections.sort(myArrayList, new MyComparator()); 

unchecked method invocation: <T>sort(java.util.List<T>,java.util.Comparator<? super T> in java.util.Collections is applied to (java.util.ArrayList,LogGrep.MyComparator) 
    Collections.sort(myArrayList, new MyComparator()); 

帮助如何解决这些将不胜感激。我在网上查看并尝试了各种所显示的内容,但我似乎无法正确理解。

注:如果我把ArrayList<Object> myArrayList = new ArrayList<Object> ...错误更改:

unchecked method invocation <T>sort(java.util.List<T>,java.util.Comparator<> super T?) in java.util.Collections is applied ot (java.util.ArraList<java.lang.Object>,LogGrep.MyComparator) 
     Collections.sort(myArrayList, new MyComparator()); 
+0

它没有列出我map_freq_by_date的定义,我打算在这个问题上面。它被定义为一个LinkedHashMap 。 – archcutbank

回答

4

比较器是一个通用接口。像这样做:

static class MyComparator implements Comparator<Map.Entry<String, Integer>> { 
    public int compare(Map.Entry<String, Integer> obj1, Map.Entry<String, Integer> obj2){ 
     ... 
    } 
} 

和定义列表,

List<Map.Entry<String, Integer>> myArrayList = new ArrayList<Map.Entry<String, Integer>>() 

,编译器会很高兴再次。

阅读the Generics Tutorial了解更多信息。或者Angelika Langer's Generics FAQ

顺便说一下,除非你比较需要运行参数或者具有可变的状态,你应该把它定义为一个常数,而不是每次调用

+0

我刚刚意识到你想要比较地图条目,而不是整数。在这种情况下,用'Map.Entry '替换所有出现的'Integer'。 –

+0

谢谢!这摆脱了警告。没有-Xlint选项,没有更多的警告。如果你知道,使用ArrayList 与ArrayList >有什么区别?另外,为什么需要将ArrayList更改为List? – archcutbank

+0

@ user372429 ArrayList只有一个类型变量,所以'ArrayList '不会被编译。没有必要将变量类型更改为List,但对接口进行编程被认为是很好的风格,而不是实现类型。阅读[Effective Java](http://java.sun.com/docs/books/effective/),第52项:[通过接口引用对象](http://my.safaribooksonline。com/book/programming/java/9780137150021/general-programming/ch08lev1sec8) –

0

创建一个新的实例,您应该使用Comparator<T>接口不是裸Comparator

阅读this article

0

你可以在一个类型安全的方式如下做到这一点:

Map<String, Integer> map = new LinkedHashMap<String, Integer>(); 
map.put("four", 4); 
map.put("one", 1); 
map.put("five", 5); 
map.put("three", 3); 
map.put("two", 2); 

System.out.println(map); 

List<Map.Entry<String, Integer>> entryList = new ArrayList<Map.Entry<String, Integer>>(map.entrySet());   
Collections.sort(entryList, new Comparator<Map.Entry<String, Integer>>() { 
    @Override 
    public int compare(Map.Entry<String, Integer> e1, Map.Entry<String, Integer> e2) { 
     return e1.getValue().compareTo(e2.getValue()); 
    }    
});   
map.clear();   
for(Map.Entry<String, Integer> e : entryList) { 
    map.put(e.getKey(), e.getValue()); 
} 

System.out.println(map); 

输出:

 
{four=4, one=1, five=5, three=3, two=2} 
{one=1, two=2, three=3, four=4, five=5}