Comparable与Comparator的具体应用场景

来源:互联网 发布:2017音乐软件市场份额 编辑:程序博客网 时间:2024/05/17 15:16
在项目开发中,我们经常要对一组数据进行排序,或者升序或者降序,在Java中排序有多种方式,最土的方式就是自己写排序算法,比如冒泡排序、快速排序、二叉树排序等,但一般不需要自己写,JDK已经为我们提供了很多的排序算法,我们采用"拿来主义" 就成了。在Java中,要想给数据排序,有两种实现方式,一种是实现Comparable接口,一种是实现Comparator接口,这两者有什么区别呢?我们来看一个例子,就比如给公司职员按照工号排序吧,先定义一个职员类代码,如下所示:
public class Employee implements Comparable<Employee>{    private int id;    private String name;    private Position position;    public Employee(int id,String name,Position position){        this.id = id;        this.name = name;        this.position = position;    }    public int getId() {        return id;    }    public void setId(int id) {        this.id = id;    }    public String getName() {        return name;    }    public void setName(String name) {        this.name = name;    }    public Position getPosition() {        return position;    }    public void setPosition(Position position) {        this.position = position;    }     //我是按照Id升序排列    @Override    public int compareTo(Employee o) {        if(this.id > o.id){            return 1;        }else if(this.id < o.id){            return -1;        }else            return 0;    }    public String toString(){        return "编号:" + this.id + "姓名:" + this.name + "职位:" + this.position;    }    enum Position{        Boss,Manager,Staff    }    }

编写客户端程序进行测试:

public class Client {    public static void main(String[] args){        List<Employee> list = new ArrayList<>(5);        list.add(new Employee(1004,"sd",Employee.Position.Staff));        list.add(new Employee(1005,"sa", Employee.Position.Staff));        list.add(new Employee(1002,"ls", Employee.Position.Manager)) ;        list.add(new Employee(1003,"ww", Employee.Position.Manager));        list.add(new Employee(1001,"zs", Employee.Position.Boss));        System.out.println(List.class);        //按照id升序排列,如果想按照名字升序排列就要用到Comparator        Collections.sort(list);        for(Employee e:list){            System.out.println(e);        }    }}
这里只是依据id进行的排序,这就是Employee默认的排序算法,但是,有时候我们希望按照职位来排序,职位一样的话我在根据id排序那怎么做呢?此时,重构Employee类已经不合适了,Employee已经是一个稳定类,为了排序功能修改它不是一个好办法,哪有什么好的解决办法吗?

有办法,看Collections.sort方法,它有一个重载方法Collections.sort(List<T>  list, Comparator<? super T> c),可以接收一个Comparator实现类,这下就好办了,在Employee类中增加一段代码即可代码如下:

static class PositionComparator implements Comparator<Employee>{        @Override        public int compare(Employee o1, Employee o2) {            int len1 = o1.getPosition().toString().length();            int len2 = o2.getPosition().toString().length();            //找到他们两个长度的最小值            int minLen = Math.min(len1,len2);            char[] v1 = o1.getPosition().toString().toCharArray();            char[] v2 = o2.getPosition().toString().toCharArray();            int k = 0;            while(k < minLen){                char vp = v1[k];                char vl = v2[k];                if(vp != vl){                   return vl - vp;                }else{                    break;                }            }            //如果职位相同再按照工号排序                if(o1.getId() > o2.getId()){                    return -1;                }else if(o1.getId() < o2.getId()){                    return 1;                }else                    return 0;            }    }
如果想改变排序方式在compare方法中改变vl,vp的位置就可以办到了
!!!Comparable接口可以作为实现类的默认排序算法,Comparator接口则是一个类的扩展排序工具

参考原文:参考文章

 
原创粉丝点击