首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >如何在不同的时间按不同的参数对列表进行排序

如何在不同的时间按不同的参数对列表进行排序
EN

Stack Overflow用户
提问于 2009-09-14 12:43:10
回答 8查看 91.8K关注 0票数 95

我有一个名为Person的类,它有多个属性,例如:

代码语言:javascript
复制
public class Person {
    private int id;
    private String name, address;
    // Many more properties.
}

很多Person-objects都存储在ArrayList<Person>中。我希望通过多个排序参数对此列表进行排序,并且有时会有所不同。例如,我可能一次想要按name升序排序,然后按address降序排序,另一次只按id降序排序。

而且我不想创建自己的排序方法(即,我想使用Collections.sort(personList, someComparator)。实现这一目标的最优雅的解决方案是什么?

EN

回答 8

Stack Overflow用户

回答已采纳

发布于 2009-09-14 13:26:34

我认为您的枚举方法基本上是合理的,但是switch语句确实需要一种更面向对象的方法。考虑一下:

代码语言:javascript
复制
enum PersonComparator implements Comparator<Person> {
    ID_SORT {
        public int compare(Person o1, Person o2) {
            return Integer.valueOf(o1.getId()).compareTo(o2.getId());
        }},
    NAME_SORT {
        public int compare(Person o1, Person o2) {
            return o1.getFullName().compareTo(o2.getFullName());
        }};

    public static Comparator<Person> decending(final Comparator<Person> other) {
        return new Comparator<Person>() {
            public int compare(Person o1, Person o2) {
                return -1 * other.compare(o1, o2);
            }
        };
    }

    public static Comparator<Person> getComparator(final PersonComparator... multipleOptions) {
        return new Comparator<Person>() {
            public int compare(Person o1, Person o2) {
                for (PersonComparator option : multipleOptions) {
                    int result = option.compare(o1, o2);
                    if (result != 0) {
                        return result;
                    }
                }
                return 0;
            }
        };
    }
}

一个使用示例(使用静态导入)。

代码语言:javascript
复制
public static void main(String[] args) {
    List<Person> list = null;
    Collections.sort(list, decending(getComparator(NAME_SORT, ID_SORT)));
}
票数 194
EN

Stack Overflow用户

发布于 2009-09-14 13:09:54

您可以为您可能想要排序的每个属性创建比较器,然后尝试“比较器链”:-)如下所示:

代码语言:javascript
复制
public class ChainedComparator<T> implements Comparator<T> {
    private List<Comparator<T>> simpleComparators; 
    public ChainedComparator(Comparator<T>... simpleComparators) {
        this.simpleComparators = Arrays.asList(simpleComparators);
    }
    public int compare(T o1, T o2) {
        for (Comparator<T> comparator : simpleComparators) {
            int result = comparator.compare(o1, o2);
            if (result != 0) {
                return result;
            }
        }
        return 0;
    }
}
票数 25
EN

Stack Overflow用户

发布于 2009-09-14 12:43:29

一种方法是创建一个Comparator,它将属性列表作为参数进行排序,如本例所示。

代码语言:javascript
复制
public class Person {
    private int id;
    private String name, address;

    public static Comparator<Person> getComparator(SortParameter... sortParameters) {
        return new PersonComparator(sortParameters);
    }

    public enum SortParameter {
        ID_ASCENDING, ID_DESCENDING, NAME_ASCENDING,
        NAME_DESCENDING, ADDRESS_ASCENDING, ADDRESS_DESCENDING
    }

    private static class PersonComparator implements Comparator<Person> {
        private SortParameter[] parameters;

        private PersonComparator(SortParameter[] parameters) {
            this.parameters = parameters;
        }

        public int compare(Person o1, Person o2) {
            int comparison;
            for (SortParameter parameter : parameters) {
                switch (parameter) {
                    case ID_ASCENDING:
                        comparison = o1.id - o2.id;
                        if (comparison != 0) return comparison;
                        break;
                    case ID_DESCENDING:
                        comparison = o2.id - o1.id;
                        if (comparison != 0) return comparison;
                        break;
                    case NAME_ASCENDING:
                        comparison = o1.name.compareTo(o2.name);
                        if (comparison != 0) return comparison;
                        break;
                    case NAME_DESCENDING:
                        comparison = o2.name.compareTo(o1.name);
                        if (comparison != 0) return comparison;
                        break;
                    case ADDRESS_ASCENDING:
                        comparison = o1.address.compareTo(o2.address);
                        if (comparison != 0) return comparison;
                        break;
                    case ADDRESS_DESCENDING:
                        comparison = o2.address.compareTo(o1.address);
                        if (comparison != 0) return comparison;
                        break;
                }
            }
            return 0;
        }
    }
}

然后可以在代码中使用它,例如:

代码语言:javascript
复制
cp = Person.getComparator(Person.SortParameter.ADDRESS_ASCENDING,
                          Person.SortParameter.NAME_DESCENDING);
Collections.sort(personList, cp);
票数 16
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1421322

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档