Java 中对象,只能进行 == 或 != ,不能使用 > 或 <,但是在开发场景中,需要对多个对象进行排序,即需要比较对象的大小
1. Comparable 接口
<自然排序>
1.1 步骤
1)实现了Comparable 接口
2)重写了compareTo()
① 如果当前对象大于形参对象obj ,则返回正整数;
② … 小于obj,返回负整数;
③ … 等于obj,返回零。
1.2 包裹类排序
包裹类已经实现了Comparable 接口,并重写了compareTo(obj) 方法,进行了从小到大排序;
public final class String
implements java.io.Serializable, Comparable<String>, CharSequence {
public int compareTo(String anotherString) {
int len1 = value.length;
int len2 = anotherString.value.length;
int lim = Math.min(len1, len2);
char v1[] = value;
char v2[] = anotherString.value;
int k = 0;
while (k < lim) {
char c1 = v1[k];
char c2 = v2[k];
if (c1 != c2) {
return c1 - c2;
}
k++;
}
return len1 - len2;
}
}
以字符串类为例,使用Arrays.sort(strArr) 方法即可直接排序;
public void test1(){
String[] strArr = new String[]{"a","s","d","f","g","h","j","k","l"};
Arrays.sort(strArr);
System.out.println(Arrays.toString(strArr));
// 输出:[a, d, f, g, h, j, k, l, s]
}
1.3 自定义类排序
1.3.1 排序类实现Comparable 接口
public class Goods implements Comparable{
...
}
1.3.2 重写compareTo(obj )
// 指明按照什么排序
@Override
public int compareTo(Object o) {
// 价格从低到高排序
if(o instanceof Goods){
Goods goods = (Goods)o;
// 方法一:
if(this.price > goods.price ){
return 1;
}else if(this.price < goods.price){
return -1;
}else {
return 0;
}
// 方法二:
// return Double.compare(this.price,goods.price);
}
throw new RuntimeException("传入的数据类型不一致");
}
1.3.3 给商品排序例
1)商品类
// 1.实现Comparable接口
public class Goods implements Comparable{
private String name;
private double price;
public Goods() {
}
public Goods(String name, double price) {
this.name = name;
this.price = price;
}
public String getName() {
return name;
}
public double getPrice() {
return price;
}
public void setName(String name) {
this.name = name;
}
public void setPrice(double price) {
this.price = price;
}
@Override
public String toString() {
return "Goods{" +
"name='" + name + '\'' +
", price=" + price +
'}';
}
// 2.重写compareTo()
// 指明按照什么排序
@Override
public int compareTo(Object o) {
// 价格从低到高排序
if(o instanceof Goods){
Goods goods = (Goods)o;
// 方法一:
if(this.price > goods.price ){
return 1;
}else if(this.price < goods.price){
return -1;
}else {
// return 0;
// 价格相同,再根据名称排序
this.name.compareTo(goods.name);
}
// 方法二:
// return Double.compare(this.price,goods.price);
}
throw new RuntimeException("传入的数据类型不一致");
}
}
2)排序
public void test2(){
Goods[] goodsArr = new Goods[3];
goodsArr[0] = new Goods("iphone",500);
goodsArr[1] = new Goods("TV",100);
goodsArr[2] = new Goods("PC",50);
Arrays.sort(goodsArr);
System.out.println(Arrays.toString(goodsArr));
// [Goods{name='PC', price=50.0}, Goods{name='TV', price=100.0}, Goods{name='iphone', price=500.0}]
}
2. Comparator 接口
<定制排序>
2.1 背景
当元素类型没有实现Comparable 接口,而又不方便修改代码,比如JDK 底层代码不可修改等情况,或者实现了Comparable 接口,但不适合当前操作,比如String 类,只能从小到大排,这时可以使用定制;
2.2 步骤
1)实现了Comparator 接口
2)重写了compare(Object o1,Object o2)
① 如果返回正整数,表示o1 大于o2;
② 如果返回负整数,表示o2 大于o1;
③ 如果返回零,表示相等。
2.3 代码实现
2.3.1 字符串
public void test1(){
String[] strArr = new String[]{"a","s","d","f","g","h","j","k","l"};
Arrays.sort(strArr, new Comparator<String>() {
// 字符串按照从大到小排序
@Override
public int compare(String o1, String o2) {
return -o1.compareTo(o2);
}
});
System.out.println(Arrays.toString(strArr));
// 输出:[s, l, k, j, h, g, f, d, a]
}
2.3.2 给商品排序例
Goods 类参照 1.3.3
public void test2(){
Goods[] goodsArr = new Goods[3];
goodsArr[0] = new Goods("iphone",500);
goodsArr[1] = new Goods("TV",100);
goodsArr[2] = new Goods("PC",50);
Arrays.sort(goodsArr, new Comparator<Goods>() {
// 产品名称从低到高,价格从高到低
@Override
public int compare(Goods o1, Goods o2) {
if(o1.getName().equals(o2.getName())){
return -Double.compare(o1.getPrice(),o2.getPrice());
}else {
return o1.getName().compareTo(o2.getName());
}
}
});
System.out.println(Arrays.toString(goodsArr));
// 输出:[Goods{name='PC', price=50.0}, Goods{name='TV', price=100.0}, Goods{name='iphone', price=500.0}]
}