【问题标题】:How to combine two Collections.sort functions如何组合两个 Collections.sort 函数
【发布时间】:2014-09-29 18:35:30
【问题描述】:

我有一个程序,其中有一个名字列表,以及有多少人有这个名字。我想按字母顺序排列名称,同时将计数从最大到最小。如果名称具有相同的计数,它会将名称按字母顺序排列。我想出了如何将名称按 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());
     }

【问题讨论】:

    标签: java sorting collections


    【解决方案1】:

    您可以制作另一个Comparator,它结合了另外两个Comparators 的效果。如果一个比较器比较相等,那么您可以调用第二个比较器并使用它的值。

    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());
    

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

    【讨论】:

      【解决方案2】:

      你可以像这样组合比较器

      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;
          }
      }
      

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

      【讨论】:

        【解决方案3】:

        假设您使用的是 Apache Commons Collections API,您可能需要查看ComparatorUtils.chainedComparator

        Collections.sort(oneName, ComparatorUtils.chainedComparator(new OneNameCompare(), new OneNameCountCompare());
        

        【讨论】:

          【解决方案4】:

          使用 Java 8 中的 lambda:

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

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2010-11-20
            • 1970-01-01
            • 2014-07-22
            • 1970-01-01
            • 2022-09-28
            • 2018-01-27
            • 1970-01-01
            相关资源
            最近更新 更多