浅析 Comparable和 Comparator的区别

浅析 Comparable和 Comparator的区别简介 Comparable 和 Comparator 都是 java util 包下的两个接口 从字面上看这两个接口都是用来做比较用的 但是 jdk 里面不可能定义两个功能相同的接口 所以他们肯定有不同的用处 1 Comparable1 1 说明 Comparable 可以认为是一个内比较器 实现了 Comparable 接口的类有一个特点 就是这些 类是可以和自己比较的 至于具体和另一个实现了 Compar

简介

Comparable和 Comparator都是java.util包下的两个接口,从字面上看这两个接口都是用来做比较用的,但是jdk里面不可能定义两个功能相同的接口,所以他们肯定有不同的用处。

1、Comparable

1.1 说明
Comparable可以认为是一个内比较器,实现了Comparable接口的类有一个特点,就是这些 类是可以和自己比较的,至于具体和另一个实现了Comparable接口的类如何比较,则依赖compareTo方法的实现,compareTo方法也被称为自然比较方法。如果开发者add进入一个Collection的对象想要Collections的sort方法帮你自动进行排序的话,那么这个对象必须实现Comparable接口。compareTo方法的返回值是int,有三种情况:

1、比较者大于被比较者(也就是compareTo方法里面的对象),那么返回正整数 2、比较者等于被比较者,那么返回0 3、比较者小于被比较者,那么返回负整数 

1.2 举例
1.定义一个Girl.java类,实现Comparable接口,并且重写compareTo方法:默认比较的是当前Girl类,通过age属性进行比较。

public class Girl implements Comparable  { private String name; private int age; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public Girl(String name, int age) { super(); this.name = name; this.age = age; } @Override public String toString() { return "Girl [name=" + name + ", age=" + age + "]"; } @Override public int compareTo(Object o) { Girl g = (Girl)o; return this.age - g.getAge(); } } 

2.定义测试类Test.java,定义一个ArrayList保存75个Girl,打乱顺序后(因为List本身是有序的),查看输出结果。代码如下:

public static void main(String[] args) { List 
  
    list = new ArrayList<>(100); Girl girl; for (int i=0; i<75; i++) { girl = new Girl("girl " + i, i); list.add(girl); } Collections.shuffle(list); list.stream().forEach(System.out::println); } 
  

3、还是2中的方法,只不过添加一行代码:使用Collections的sort(T t)方法排序

public static void main(String[] args) { List 
  
    list = new ArrayList<>(100); Girl girl; for (int i=0; i<75; i++) { girl = new Girl("girl " + i, i); list.add(girl); } Collections.shuffle(list); Collections.sort(list); list.stream().forEach(System.out::println); } 
  

2、Comparator

2.1 说明
Comparator可以认为是是一个外比较器,个人认为有两种情况可以使用实现Comparator接口的方式:
1、一个对象不支持自己和自己比较(没有实现Comparable接口),但是又想对两个对象进行比较。
2、一个对象实现了Comparable接口,但是开发者认为compareTo方法中的比较方式并不是自己想要的那种比较方式。
Comparator接口里面有一个compare方法,方法有两个参数T o1和T o2,是泛型的表示方式,分别表示待比较的两个对象,方法返回值和Comparable接口一样是int,有三种情况:








 1、o1大于o2,返回正整数 2、o1等于o2,返回0 3、o1小于o3,返回负整数 

2.2 举例
1.定义一个Girl.java类如下:

public class Girl { private String name; private int age; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public Girl(String name, int age) { super(); this.name = name; this.age = age; } @Override public String toString() { return "Girl [name=" + name + ", age=" + age + "]"; } } 

2.定义GirlComparator.java类,实现Comparator接口,重写compare()方法,和前面一样根据age进行比较。

public class GirlComparator implements Comparator 
  
    { @Override public int compare(Girl g1, Girl g2) { return g1.getAge() - g2.getAge(); } } 
  

2.定义测试类Test.java,定义一个TreeSet保存75个Girl,查看输出结果。代码如下:

public static void main(String[] args) { Set 
  
    set = new TreeSet<>(); Girl girl; for (int i = 0; i< 75; i++) { girl = new Girl("girl "+i, i); set.add(girl); } set.stream().forEach(System.out::println); } 
  

3、总结

总结一下,这两种比较器Comparable和Comparator,后者相比前者有如下优点:

  • 个性化比较:如果实现类没有实现Comparable接口,又想对两个类进行比较(或者实现类实现了Comparable接口,但是对compareTo方法内的比较算法不满意),那么可以实现Comparator接口,自定义一个比较器,写比较算法。
  • 解耦:实现Comparable接口的方式比实现Comparator接口的耦合性要强一些,如果要修改比较算法,要修改Comparable接口的实现类,而实现Comparator的类是在外部进行比较的,不需要对实现类有任何修改。从这个角度说,其实有些不太好,尤其在我们将实现类的.class文件打成一个.jar文件提供给开发者使用的时候。
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/219551.html原文链接:https://javaforall.net

(0)
上一篇 2026年3月17日 下午10:18
下一篇 2026年3月17日 下午10:18


相关推荐

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号