排序列表<>没有按预期工作

时间:2015-11-25 06:31:28

标签: java string list sorting comparator

如何在java az 日期中排序List<>或从更大到更低中的任何内容进行排序从低到大等?

我对此进行了大量搜索,发现Collections仅从a-z排序,但它首先将大写排序,然后排在小写

例如:

// Must be like this
Best
best
Book
Bus

// But it's returns this
Best
Book
Bus
best

它也很慢,我看到其他应用程序在5秒内加载排序列表。我的需要15或20秒!

代码:

Collections.sort(posts, new Comparator<Post>() {
            @Override
            public int compare(Post lhs, Post rhs) {
                return lhs.getName().compareTo(rhs.getName());
            }
        });

3 个答案:

答案 0 :(得分:4)

使用String.compareToIgnoreCase可能会更有效:

Collections.sort(posts, new Comparator<Post>() {
     @Override
     public int compare(Post lhs, Post rhs) {
         return lhs.getName().compareToIgnoreCase(rhs.getName());
     }
});

这样你就不会创建中间字符串(比如@TimBiegeleisen的回答),但是就地比较它们。

请注意,它在Java-8中更简单:

Collections.sort(posts, Comparator.comparing(Post::getName, String.CASE_INSENSITIVE_ORDER));

答案 1 :(得分:3)

使用String.toLowerCase()来处理您的单词大写的问题:

Collections.sort(posts, new Comparator<Post>() {
        @Override
        public int compare(Post lhs, Post rhs) {
            String left  = lhs.getName().toLowerCase();
            String right = rhs.getName().toLowerCase();

            if (left.equals(right)) {
                return lhs.getName().compareTo(rhs.getName());
            }
            else {
                return left.compareTo(right);
            }
});

如果您还希望在排序中包含大小和日期等内容,则可以修改compare()方法以将其考虑在内。例如,要按名称(第一个)和大小(第二个)进行比较,请使用以下代码:

Collections.sort(posts, new Comparator<Post>() {
     @Override
     public int compare(Post lhs, Post rhs) {
         int nameComp = lhs.getName().compareToIgnoreCase(rhs.getName());
         if (nameComp == 0) {
             Integer lhsSize = lhs.getSize();
             Integer rhsSize = rhs.getSize();

             return lhsSize.compareTo(rhsSize);
         }
         else {
             return nameComp;
         }
     }
});

答案 2 :(得分:0)

现有答案的补充。

通过“首先转换为小写然后比较”进行大小写忽略的比较的方法无效,因为不必要地创建了新的String对象。

更合适的方法是使用String.compareIgnoreCase()String.CASE_INSENSITIVE_ORDER比较器。

而且,如果OP对第三方库开放,使用Guava或Apache Common Langs可能会使您的代码更容易阅读,如果您要比较多个属性,例如使用Guava:

Collections.sort(posts, new Comparator<Post>() {
    @Override
    public int compare(Post lhs, Post rhs) {
        return ComparatorChain.start()
                .compare(lhs.getName(), rhs.getName(), String.CASE_INSENSITIVE_ORDER)
                .compare(lhs.getName(), rhs.getName())
                .compare(lhs.getDate(), rhs.getDate()) 
                .compare(lhs.getId(), rhs.getId())
                .result();
    }
});