development

개체 컬렉션 정렬

big-blog 2020. 12. 11. 19:06
반응형

개체 컬렉션 정렬


이 질문에 이미 답변이 있습니다.

간단한 문자열 목록이있는 경우 :

List<String> stringList = new ArrayList<String>();

다음과 같이 정렬 할 수 있습니다.

Collections.sort(stringList);

그러나 Person 클래스가 있다고 가정합니다.

public class Person
{
   private String name;
   private Integer age;
   private String country;
}

그리고 그것의 목록 ​​:

List<Person> personList = new ArrayList<Person>();

때로는 이름, 나이, 국가별로 정렬하고 싶습니다.

이를 달성하는 가장 쉬운 방법은 무엇입니까?

Comparable 인터페이스를 구현할 수 있다는 것을 알고 있지만 하나의 특정 속성으로 정렬하도록 제한하는 것 같습니다.


Comparator 인터페이스를 구현하고 (각기 다른 정렬 순서에 대해 한 번씩 ) Comparator를 추가 매개 변수로 사용하는 Collections.sort () 메서드를 사용합니다 .


Collections.sort는 사용자 지정 비교기를 사용하여 호출 할 수 있습니다. 그리고 그 비교기를 구현하여 다른 정렬 순서로 정렬 할 수 있습니다. 다음은 예입니다 (Person 모델의 경우-연령을 정수로 사용).

public class FlexiblePersonComparator implements Comparator<Person> {
  public enum Order {Name, Age, Country}

  private Order sortingBy = Name;

  @Override
  public int compare(Person person1, Person person2) {
    switch(sortingBy) {
      case Name: return person1.name.compareTo(person2.name);
      case Age: return person1.age.compareTo(person2.age);
      case Country: return person1.country.compareTo(person2.country);
    }
    throw new RuntimeException("Practically unreachable code, can't be thrown");
  }

  public void setSortingBy(Order sortBy) {
    this.sortingBy = sortingBy;
  }
}

다음과 같이 사용합니다 (사람이 필드라고 가정).

public void sortPersonsBy(FlexiblePersonComparator.Order sortingBy) {
  List<Person> persons = this.persons;  // useless line, just for clarification
  FlexiblePersonComparator comparator = new FlexiblePersonComparator();
  comparator.setSortingBy(sortingBy);
  Collections.sort(persons, comparator); // now we have a sorted list
}

응답자 덕분입니다. 다른 사람들의 이익을 위해 완전한 예를 포함하고 싶습니다.

해결책은 다음과 같은 추가 클래스를 만드는 것입니다.

public class NameComparator implements Comparator<Person>
{
    public int compare(Person o1, Person o2)
    {
       return o1.getName().compareTo(o2.getName());
   }
}

public class AgeComparator implements Comparator<Person>
{
    public int compare(Person o1, Person o2)
    {
        return o1.getAge().compareTo(o2.getAge());
    }
}

public class CountryComparator implements Comparator<Person>
{
    public int compare(Person o1, Person o2)
    {
        return o1.getCountry().compareTo(o2.getCountry());
    }
}

그런 다음 목록을 다음과 같이 정렬 할 수 있습니다.

Collections.sort(personList, new NameComparator());
Collections.sort(personList, new AgeComparator());
Collections.sort(personList, new CountryComparator());

이를 수행하는 Java 8 방법은 List.sort다음과 같이 사용 하는 것입니다.

personList.sort(Comparator.comparing(Person::getName));

Stuart Marks 의 답변을 여기인용 합니다 .

This is the big advantage of the List.sort(cmp) extension method over Collections.sort(list, cmp). It might seem that this is merely a small syntactic advantage being able to write myList.sort(cmp) instead of Collections.sort(myList, cmp). The difference is that myList.sort(cmp), being an interface extension method, can be overridden by the specific List implementation. For example, ArrayList.sort(cmp) sorts the list in-place using Arrays.sort() whereas the default implementation implements the old copyout-sort-copyback technique.


You could also use the BeanComparator from apache commons beanutils, like this:

Collections.sort(personList, new BeanComparator("name"));

Implement 3 different types of Comparator.

you can add the comparator to the sort command. The comparator you define, will sort the elements by name, age, or what ever.

Collections.sort(list, new Comparator() {

        public int compare(Object arg0, Object arg1) {
            if (!(arg0 instanceof Person)) {
                return -1;
            }
            if (!(arg1 instanceof Person)) {
                return -1;
            }

            Person pers0 = (Person)arg0;
            Person pers1 = (Person)arg1;


            // COMPARE NOW WHAT YOU WANT
            // Thanks to Steve Kuo for your comment!
            return pers0.getAge() - pers1.getAge();
        }
    });

The Collections.sort method can be invoked with a second argument which is the comparator to use. Create 3 comparators and use the one you want when appropriate.

Collections.sort(list , new Comparator() {
        public int compare(Object o1, Object o2) {
          ...
        }
      });

I asked a very similar question (about searching rather than sorting), perhaps there is some useful information (I ended up using an enum that implements Comparator so I pass the enum value as a comparator selector).


Using lambdaj ( http://code.google.com/p/lambdaj/ ) you can achieve what you're asking in the following way:

sort(personList, on(Person.class).getName());

sort(personList, on(Person.class).getAge());

sort(personList, on(Person.class).getCountry());

참고URL : https://stackoverflow.com/questions/1206073/sorting-a-collection-of-objects

반응형