有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java如何组合两个集合。排序函数

我有一个程序,其中有一个名字列表,以及有多少人有这个名字。我想把名字按字母顺序排列,同时把计数从大到小排列。如果名称的计数相同,则按字母顺序排列名称。我知道如何把名字按abc顺序排列,也知道如何把计数从大到小排列,但我不知道如何把两者结合起来,得到从大到小排列的名字列表,以及它们是否按字母顺序排列有相同的计数

 Collections.sort(oneName, new OneNameCompare());
    for(OneName a: oneName)
    {
     System.out.println(a.toString());

    }
 Collections.sort(oneName, new OneNameCountCompare());
     for(OneName a: oneName)
    {

     System.out.println(a.toString());
     }

共 (4) 个答案

  1. # 1 楼答案

    假设您使用的是Apache Commons Collections API,那么您可能想查看^{}

    Collections.sort(oneName, ComparatorUtils.chainedComparator(new OneNameCompare(), new OneNameCountCompare());
    
  2. # 2 楼答案

    使用Java 8中的lambdas:

    Collections.sort(Arrays.asList(""),
            (e1, e2) -> e1.getName().compareTo(e2.getName()) != 0 ?
                    e1.getName().compareTo(e2.getName()) :
                    e1.getCount().compareTo(e2.getCount()));
    
  3. # 3 楼答案

    您可以创建另一个Comparator,它结合了其他两个Comparator的效果。如果一个比较器比较相等,则可以调用第二个比较器并使用其值

    public class CountNameComparator implements Comparator<Name>
    {
        private OneNameCompare c1 = new OneNameCompare();
        private OneNameCountCompare c2 = new OneNameCountCompare();
        @Override
        public int compare(Name n1, Name n2)
        {
            int comp = c1.compare(n1, n2);
            if (comp != 0) return comp;
            return c2.compare(n1, n2);
        }
    }
    

    然后你可以只打一次电话Collections.sort

    Collections.sort(oneName, new CountNameComparator());
    

    这可以推广到任何数量的比较器

  4. # 4 楼答案

    你可以这样组合比较器

    public static <T> Comparator<T> combine(final Comparator<T> c1, final Comparator<T> c2) {
        return new Comparator<T>() {
           public int compare(T t1, T t2) {
              int cmp = c1.compare(t1, t2);
              if (cmp == 0)
                  cmp = c2.compare(t1, t2);
              return cmp;
           }
        };
    }
    

    顺便说一句,比较器是何时使用无状态单例的一个很好的例子。所有比较器或类型都是相同的,所以您只需要其中一个

    public enum OneNameCompare implements Comparator<OneName> {
        INSTANCE;
        public int compare(OneName o1, OneName o2) {
            int cmp = // compare the two objects
            return cmp;
        }
    }
    

    这样可以避免创建新实例或缓存副本。你只需要每种类型中的一种