java에서 Comparable와 Comparator 상세 설명 및 비교
6434 단어 javaComparableComparator
오늘 TreeMap의 원본 코드를 보니 키가Comparable이나Comparator의 인터페이스를 실현해야 할 때 약간의 흥미가 생겼다. 예를 들어 TreeMap에서의put방법은 각각Comparable와Comparator 인터페이스를 각각 처리하는 것이다.그렇다면 의문이 온다. Comparable과Comparator 인터페이스의 차이점은 무엇입니까? 자바에 왜 두 개의 유사한 인터페이스가 존재합니까?
Comparable와 Comparator 인터페이스는 모두 크기를 비교하는 데 쓰인다. 우선 Comparable의 정의를 살펴보자.
package java.lang;
import java.util.*;
public interface Comparable<T> {
public int compareTo(T o);
}
Comparator의 정의는 다음과 같습니다.
package java.util;
public interface Comparator<T> {
int compare(T o1, T o2);
boolean equals(Object obj);
}
Comparable은 이를 실현하는 모든 종류의 대상을 전체적으로 정렬합니다.이 인터페이스는 클래스 자체가 실현되어야 한다.하나의 클래스가 Comparable 인터페이스를 실현하면, Comparable 인터페이스를 실현하는 클래스의 대상 목록(또는 그룹)은 Collections를 통해 사용할 수 있습니다.정렬하려면 sort 또는 Arrays.sort 를 선택합니다.또한 Comparable 인터페이스를 구현하는 클래스의 객체는 비교기를 지정하지 않고도 [TreeMap)]의 키 또는 [TreeSet]의 요소로 사용할 수 있습니다.예(클래스Person1은 Comparable 인터페이스를 구현함)
package collections;
public class Person1 implements Comparable<Person1>
{
private int age;
private String name;
public Person1(String name, int age)
{
this.name = name;
this.age = age;
}
@Override
public int compareTo(Person1 o)
{
return this.age-o.age;
}
@Override
public String toString()
{
return name+":"+age;
}
}
는 Person1이 Comparable 인터페이스의compareTo 방법을 실현한 것을 볼 수 있다.Comparable 인터페이스를 실현하려면 반드시 자신의 클래스, 즉 자신의 클래스에서 인터페이스를 실현하는 상응하는 방법을 수정해야 한다.테스트 코드:
Person1 person1 = new Person1("zzh",18);
Person1 person2 = new Person1("jj",17);
Person1 person3 = new Person1("qq",19);
List<Person1> list = new ArrayList<>();
list.add(person1);
list.add(person2);
list.add(person3);
System.out.println(list);
Collections.sort(list);
System.out.println(list);
출력 결과:
[zzh:18, jj:17, qq:19]
[jj:17, zzh:18, qq:19]
만약에 우리의 이런 종류가 수정할 수 없다면, 예를 들어 String과 같이 우리는 그것에 대해 정렬을 해야 한다. 물론 String에서는Comparable 인터페이스가 실현되었기 때문에 단순히 String을 예로 들면 그다지 형상적이지 않다.클래스 자체를 수정할 수 없습니다. 이것은Comparator라는 인터페이스(정책 모드)에 사용됩니다.
public final class Person2
{
private int age;
private String name;
public Person2(String name, int age)
{
this.name = name;
this.age = age;
}
@Override
public String toString()
{
return name+":"+age;
}
//getter and setter ....
}
클래스Person2와 같이 이 클래스는 이미 고정되어 그 클래스 자체에 대한 수정을 진행할 수 없고 수식어final도 있습니다. 당신도 더 이상implementsComparable를 계승할 생각은 하지 마세요. 그러면 이때 어떻게 해야 합니까?클래스 외부에서 Comparator 인터페이스를 사용합니다.다음 테스트 코드:
Person2 p1 = new Person2("zzh",18);
Person2 p2 = new Person2("jj",17);
Person2 p3 = new Person2("qq",19);
List<Person2> list2 = new ArrayList<Person2>();
list2.add(p1);
list2.add(p2);
list2.add(p3);
System.out.println(list2);
Collections.sort(list2,new Comparator<Person2>(){
@Override
public int compare(Person2 o1, Person2 o2)
{
if(o1 == null || o2 == null)
return 0;
return o1.getAge()-o2.getAge();
}
});
System.out.println(list2);
출력 결과:
[zzh:18, jj:17, qq:19]
[jj:17, zzh:18, qq:19]
여기(public static예를 들어 블로거가 만난 실제 사례에서 String에 대해 정렬을 해야 하고 대소문자를 구분하지 않아야 한다. 우리는 String의 정렬이 사전 정렬이라는 것을 안다. 예를 들어 A a D 정렬 다음에 A D a라는 것은 분명히 옳지 않다. 그러면 어떻게 해야 합니까?위와 같음(아래 코드의 list는 String의 List 컬렉션입니다):
Collections.sort(list, new Comparator<String>()
{
@Override
public int compare(String o1, String o2)
{
if(o1 == null || o2 == null)
return 0;
return o1.toUpperCase().compareTo(o2.toUpperCase());
}
});
이렇게 하면 크기를 구분하지 않고 정렬하는 String의 집합을 실현할 수 있으니 편리하지 않아요~세심한 학우들은 분명히 Comparator 인터페이스에서 두 가지 방법을 정의했는데 왜 계승할 때 한 가지 방법만 실현했는지 의문이 생길 수 있다. 설마 내가 자바 인터페이스 상식에 대한 이해를 전복시키려는 것은 아니겠지.
실제로 우리는 한 종류가 현식 상속 부류가 없을 때 기본적인 부류, 즉java가 있다는 것을 안다.lang.Object, Object 클래스 중 하나의 방법은 equals 방법이기 때문에 Comparator 인터페이스를 실현하는 클래스는 equals 방법을 실현하도록 강요하지 않습니다. 부모 클래스를 직접 호출하면 됩니다. 비록 당신이 현저하게 equals () 방법을 실현했지만 will be a better choice~
'Effective Java'라는 책에서 저자 조슈아 블락은 사용자 정의 클래스를 작성할 때 가능한 한 Comparable 인터페이스를 실현하는 것을 추천한다. 일단 Comparable 인터페이스를 실현하면 많은 범용 알고리즘과 인터페이스 개선에 의존하는 집합과 협업할 수 있다.네가 아주 작은 노력을 기울이면 매우 강력한 기능을 얻을 수 있다.
사실상 자바 플랫폼 라이브러리의 모든 값 클래스는Comparable 인터페이스를 실현했다.만약 당신이 값 종류를 작성하고 있다면, 그것은 알파벳 순서, 수치 순서, 연대 순서 등 매우 뚜렷한 내재적인 정렬 관계를 가지고 있다면, 이 인터페이스를 실현하는 것을 단호히 고려해야 한다.
compareTo 방법은 간단한 등동성 비교를 허용할 뿐만 아니라 어순 집행 순서 비교도 허용한다. 이외에 이것은 Object의 equals 방법과 비슷한 특징을 가지고 범형이다.클래스는Comparable 인터페이스를 실현했다. 이것은 그 실례가 내재적인 정렬 관계를 가지고 있음을 나타낸다. Comparable 인터페이스를 실현하기 위한 대상 수조를 정렬하는 것은 이렇게 간단하다:Arrays.sort(a);
는 집합에 저장된Comparable 대상을 검색하고 극한값을 계산하며 자동 유지보수도 간단하다.예를 들어, 다음 프로그램은 String에 의존하여 Comparable 인터페이스를 구현하여 명령행 매개변수 목록에서 반복 매개변수를 제거하고 알파벳순으로 인쇄합니다.
public class WordList{
public static void main(String args[]){
Set<String> s = new TreeSet<String>();
Collections.addAll(s,args);
System.out.println(s);
}
}
Comparable은 정렬 인터페이스입니다.클래스가 Comparable 인터페이스를 구현하면 클래스 지원 정렬을 의미합니다.Comparator는 비교기입니다.우리가 만약 어떤 종류의 순서를 제어해야 한다면,'이류의 비교기'를 만들어서 정렬할 수 있다.전자는 비교적 고정적이고 구체적인 종류와 연결되어야 하며 후자는 비교적 유연하여 각 비교 기능이 필요한 종류에 사용할 수 있다.전자는'정적 귀속'에 속하고 후자는'동적 귀속'에 속한다고 할 수 있다.
우리는 발견하기 어렵지 않다. Comparable는'내부 비교기'에 해당하고, Comparator는'외부 비교기'에 해당한다.
읽어주셔서 감사합니다. 여러분에게 도움이 되었으면 좋겠습니다. 본 사이트에 대한 지지에 감사드립니다!
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
38. Java의 Leetcode 솔루션텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.