前几天去oracle面试,考官出了这样一个题:
student类有id,name,score三个属性,现在又许多student实例,问:实现对student的name,score的排序(包括升序和降序两种)。
我是这样写的,我写了4个comparator(分别是按name升序、按name降序,按score升序,按score降序),他们都实现Comparator接口,并且我自己仿照Arrays.sort(Object[] a)写了自己的快排算法,实现了考官的功能,但是考官说加入我让你也对id排序,那么你还新建两个comparator吗?当时我就不会了。
大家能不能利用面向对象的思想设计一下这个排序,达到代码的复用,不论按照哪个属性排序都不会新建类,或者说不论排序需求是不变化是否增加都不用再创建新的comparator,给个设计方案就好

解决方案 »

  1.   

    大概这么写吧。public class StudentComparator implements Comparator<Student> {
    private String property;

    private int order;

    public StudentComparator(String property, int order) {
    this.property = property;
    this.order = order;
    } @Override
    public int compare(Student o1, Student o2) {
    // TODO: 根据property得到比较的属性,order得到顺序还是逆序。
    return 0;
    }
    }
      

  2.   

    实现一个Comparator,假定类名为C
    C.setOrderingProperty(),设置排序用的属性名
    C.setOrderingDirection(),设置升序还是降序排序
    C.Compare(O1,O2),根据设置的属性名,通过反射取O1,O2的相应属性,并且区分其是数字还是字符串,根据之前设置的升降序进行比较
      

  3.   

    在public int compare(Student o1, Student o2)方法中,加入我想比较o1和o2的property属性,应当这样写吧:
    Student.class.getField(property).get(o1);//获得o1的property属性
    Student.class.getField(property).get(o2);//获得o2的property属性
    但是我怎么比较这两个属性,我不知道这两个属性到底是String还是int或者是其他的类型,我是用大于号比较还是用Object类的comparaTo方法比较?
      

  4.   

    我觉得考官主要在问关于升序降序的问题所在,注意考官说的2,对于每一个属性创建一个comparator也不可厚非;
    另外,升序降序没必要实现吧,Collection的排序方法里就可以指定升序还是降序。
      

  5.   

    假如我的属性不止有String,int,还有我自己定义的其他类型呢,是不是需要转型之后才能调用改类型重写了的compareTo()方法,但是我怎么知道到底转型为哪种类型?
      

  6.   

    Collections的哪个方法可以指定升序、降序?
      

  7.   

    用getClass判断Field的类型吧。这个可以写成一个工具类,还是很通用的。
      

  8.   


    如果还有你自己定义的其它类型,则你在定义的时候应该提供该类型的compare方法
    如果从程序的鲁棒性考虑,在Comparator的compare方法中可以针对这样的类型首先寻找该类型的compare方法,如果找不到,则用其它方法如getId()或者toString()来比较
      

  9.   

    是用field.getType()判断吧?
      

  10.   

    很认真地态度,不错! 我印象里记得这个sort(List<T> list, Comparator<? super T> c)看来还是要在Compoarator是做手脚。我现在倒是有一个问题,你去Oracle面试,而且考官明显是给了一个Student的table,为什么不使用SQL语句呢?
    你只要定义一个动态SQL语句就可以很轻松实现对Student的每一个字段进行升序和降序排列了。
      

  11.   

    这个应该算是 Object-Relational Maping的问题
      

  12.   

    Referto:
    http://docs.oracle.com/cd/B19306_01/appdev.102/b14260/adobjint.htm
      

  13.   

    考官给的不是数据库表,而是一个文件,所以没有办法用sql
      

  14.   

    先抛开面试不谈,对于这样的一个项目需求,一般来讲都会采用java + DB的架构来实现,如果说该项目由特殊要求不能使用数据库,那么相应记录数据会通常采用XML来存储数据,无论哪个方法,都可以用SQL,具体可以参考:
    http://www.stylusstudio.com/sqlxml_tutorial.html
    总之采用SQL是对于该种需求解决方案的方向和思路。回到面试上再谈,如果你将来面对的是oracle底层类库的开发那就另当别论,也许利用类反射机制开发一个支持多种数据类型的 comparator是一个好的选择,前面有人已经回答了,我就不赘述了。面对问题一定要搞清需求,发散思路,不能太局限于某个技术。
      

  15.   

    不知道行不行?
    http://blog.csdn.net/e437032193/article/details/6625849