疯狂java


您现在的位置: 疯狂软件 >> 新闻资讯 >> 正文

说说Java的Comparable 与 Comparator


 

 
Comparable和Comparator是Java核心API提供的两个接口。从它们的名字就可以看出,他们用于比较对象的大小。接下来的两个例子来回答这个问题。这个简单的例子就是比较两种HaHa的尺寸。当阅读完下面的代码,你就知道如何使用Comparable和Comparator。
1、Comparable
一个类实现Comparable接口,是为了可以让其自身的对象和其他对象进行比较。类本身必须实现这个接口,为的是可以和它自己的实例进行比较。要求实现的方法是compareTo()。下面的这个例子来展示它的用法:
 
package com.demo;
public class HaHa implements Comparable<HaHa>{
private int size;
private String brand;
public HaHa(int size, String brand) {
this.size = size;
this.brand = brand;
}
public int getSize() {
return size;
}
public void setSize(int size) {
this.size = size;
}
public String getBrand() {
return brand;
}
public void setBrand(String brand) {
this.brand = brand;
}
@Override
public int compareTo(HaHa ha) {
if (this.getSize() > ha.getSize()) {
return 1;
} else if (this.getSize() < ha.getSize()) {
return -1;
} else {
return 0;
}
}
}
 
package com.demo;
public class Main {
public static void main(String[] args) {
HaHa ha1 = new HaHa(55, "Samsung");
HaHa ha2 = new HaHa(60, "Sony");
if (ha1.compareTo(ha2) > 0) {
System.out.println(ha1.getBrand() + " is better.");
} else {
System.out.println(ha2.getBrand() + " is better.");
}
}
}
 
运行该程序,输入如下:
Sony is better.
2、Comparator
对于比较对象间的不同属性,Comparator能更好的胜任。例如,两个人可以基于name和age进行比较等。(这些情况,Comparable就不可以胜任了。)
必须实现compare()方法。现在,让我们使用其他方式来比较这些TV的尺寸。Comparator的常用方法是排序。Collections和Arrays类都提供了一个可以使用Comparator的排序方法。例子如下:
 
package com.demo.Comparator;
public class HaHa{
private int size;
private String brand;
public HaHa(int size, String brand) {
this.size = size;
this.brand = brand;
}
public int getSize() {
return size;
}
public void setSize(int size) {
this.size = size;
}
public String getBrand() {
return brand;
}
public void setBrand(String brand) {
this.brand = brand;
}
}
package com.demo.Comparator;
import java.util.Comparator;
 
public class SizeComparator implements Comparator<HaHa>{
@Override
public int compare(HaHa o1, HaHa o2) {
int ha1Size = o1.getSize();
int ha2Size = o2.getSize();
if(ha1Size > ha2Size){
return 1;
} else if(ha1Size < ha2Size){
return -1;
} else{
return 0;
}
}
}
package com.demo.Comparator;
 
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class Main {
public static void main(String[] args) {
HaHa ha1 = new HaHa(55, "Samsung");
HaHa ha2 = new HaHa(60, "Sony");
HaHa ha3 = new HaHa(42, "Panasonic");
List<HaHa> has = new ArrayList<HaHa>();
has.add(ha1);
has.add(ha2);
has.add(ha3);
Collections.sort(has, new SizeComparator());
for (HaHa ha : has) {
System.out.println(ha.getBrand());
}
}
}
运行改程序,输入如下:
Panasonic
Samsung
Sony
 
3、如何选择呢
简单来说,一个实现Comparable接口的类具有可比性,意思就是说它的实例相互直接可以进行比较。
一个实现Comparator接口的类就一个比较器(Comparator),相对于其他类。首先,它可以被传入排序方法,例如Collections.sort()或Arrays.sort(),可精确控制排序顺序;其次,它还可以被用于控制已有的某行数据结构的顺序,例如排序的set或排序的map。
例如,创建TreeSet,我们可以在构造函数中传入一个Comparator,或者将一个类添加可比性。
方式一:TreeSet(Comparator比较器)
package com.demo.treesetcomparator;
public class Dog {
int size;
public Dog(int size){
this.size = size;
}
@Override
public String toString(){
return "Dog{size="+size+"}";
}
}
package com.demo.treesetcomparator;
import java.util.Comparator;
public class SizeComparator implements Comparator<Dog>{
@Override
public int compare(Dog o1, Dog o2) {
return o1.size - o2.size;
}
}
package com.demo.treesetcomparator;
import java.util.TreeSet;
public class ImpComparableMain {
public static void main(String[] args) {
TreeSet<Dog> d = new TreeSet<Dog>(new SizeComparator());
d.add(new Dog(3));
d.add(new Dog(1));
d.add(new Dog(2));
System.out.println(d);
}
}
 
方式二:实现Comparable
package com.demo.treesetcomparable;
public class Dog implements Comparable<Dog> {
int size;
public Dog(int size){
this.size = size;
}
@Override
public int compareTo(Dog o) {
return o.size - this.size;
}
@Override
public String toString(){
return "Dog{size=" + size + "}";
}
}
 
package com.demo.treesetcomparable;
import java.util.TreeSet;
import com.demo.treesetcomparable.Dog;
public class ImpComparableMain {
public static void main(String[] args) {
TreeSet<Dog> d = new TreeSet<Dog>();
d.add(new Dog(3));
d.add(new Dog(1));
d.add(new Dog(2));
System.out.println(d);
}
}