文档章节

Java基础-对象排序详解

陶邦仁
 陶邦仁
发布于 2012/11/24 10:04
字数 1171
阅读 403
收藏 5

1. Comparator,Comparable接口区别

comparable是通用的接口,用户可以实现它来完成自己特定的比较,而comparator可以看成一种算法的实现,当需要容器集合 collection需要比较功能的时,来指定这个比较器,这可以看出一种设计模式,将算法和数据分离,就像C++ STL中的函数对象一样。

Comparable应该比较固定,和一个具体类相绑定,而Comparator比较灵活,它可以被用于各个需要比较功能的类使用。可以说前者属于“静态绑定”,而后者可以“动态绑定”。

一个类实现了Camparable接口表明这个类的对象之间是可以相互比较的。如果用数学语言描述的话就是这个类的对象组成的集合中存在一个全序。这样,这个类对象组成的集合就可以使用Sort方法排序了。

而Comparator的作用有两个:
1. 如果类的设计师没有考虑到Compare的问题而没有实现Comparable接口,可以通过Comparator来实现比较算法进行排序。
2. 为了使用不同的排序标准做准备,比如:升序、降序或其他什么序。

2. Arrays和Collections类区别

要知道两个类:java.util.Arrays和java.util.Collections(注意和Collection的区别),Collection是集合框架的顶层接口,而Collections是包含了许多静态方法。我们使用Arrays对数组进行排序,使用Collections对集合框架容器进行排序,如ArraysList,LinkedList等。

对数组进行排序

对基本数据类型(primitive type)或String类型的数组进行排序:

int[] intArray = new int[] {4, 1, 3, -23}; 
Arrays.sort(intArray); 
// [-23, 1, 3, 4] 
String[] strArray = new String[] {"z", "a", "C"}; 
Arrays.sort(strArray); 
// [C, a, z] 
// Case-insensitive sort 
Arrays.sort(strArray, String.CASE_INSENSITIVE_ORDER); 
// [a, C, z] 
// Reverse-order sort 
Arrays.sort(strArray, Collections.reverseOrder()); 
// [z, a, C] 
// Case-insensitive reverse-order sort 
Arrays.sort(strArray, String.CASE_INSENSITIVE_ORDER); 
Collections.reverse(Arrays.asList(strArray)); 
// [z, C, a]

当然我们也可以指定数组的某一段进行排序比如我们要对数组下表0-2的部分(假设数组长度大于3)进行排序,其他部分保持不变,我们可以使用:

Arrays.sort(strArray,0,2);

这样,我们只对前三个元素进行了排序,而不会影响到后面的部分。

对对象数组进行排序

这个数组的自然顺序是未知的,因此我们需要为该类实现Comparable接口。

Name类

public class Name implements Comparable<Name>{ 
       public String firstName, lastName; 
       public Name(String firstName,String lastName){ 
              this.firstName=firstName; 
              this.lastName=lastName; 
       } 
       public int compareTo(Name o) { //实现接口 
              int lastCmp=lastName.compareTo(o.lastName); 
              return (lastCmp!=0?lastCmp:firstName.compareTo(o.firstName)); 
       } 
       public String toString(){ //便于输出测试 
              return firstName+" "+lastName; 
       } 
}

这样,当我们对这个对象数组进行排序时,就会先比较lastName,然后比较firstName 然后得出两个对象的先后顺序,就像compareTo(Name o)里实现的那样。用程序进行测试:

NameSort类

import java.util.*; 
public class NameSort { 
        public static void main(String[] args) { 
               Name[] nameArray = new Name[]{ 
                       new Name("John", "Lennon"), 
                       new Name("Karl", "Marx"), 
                       new Name("Groucho", "Marx"), 
                       new Name("Oscar", "Grouch") 
                       }; 
              Arrays.sort(nameArray); 
              for(int i=0;i<nameArray.length;i++){ 
                       System.out.println(nameArray[i].toString()); 
              } 
        } 
}

对集合框架进行排序

如果已经理解了Arrays.sort()对数组进行排序的话,集合框架的使用也是大同小异。只是将Arrays替换成了Collections,注意Collections是一个类而Collection是一个接口。

假如有这样一个链表:

LinkedList list=new LinkedList(); 
list.add(4); 
list.add(34); 
list.add(22); 
list.add(2);

我们只需要使用:

Collections.sort(list);

就可以将list里的元素按从小到大的顺序进行排序,结果就成了: [2, 4, 22, 34]。

如果LinkedList里面的元素是String,同样会像基本数据类型一样从小到大排序。如果要实现反序排序也就是从大到小排序:

Collections.sort(list,Collectons.reverseOrder());

如果LinkedList里面的元素是自定义的对象,可以像上面的Name对象一样实现Comparable接口,就可以让Collection.sort()为您排序了。

对对象进行自定义排序

可以使用sort(List<T> list, Comparator<? super T> c)这个方法进行排序,FIRST_NAME_ORDER类。

import java.util.*; 
public class FIRST_NAME_ORDER implements Comparator<Name>{ 
          public int compare(Name n1, Name n2) { 
                  int firstCmp=n1.firstName.compareTo(n2.firstName); 
                  return (firstCmp!=0?firstCmp:n1.lastName.compareTo(n2.firstName)); 
          } 
}

在上面的NameSort中将 Arrays.sort(nameArray);替换成下面语句

List<Name> list=Arrays.asList(nameArray); // 将名字数组转化为List 
Collections.sort(list,new FIRST_NAME_ORDER());

下面举例根据TreeMap的key进行降序排序

import java.util.*; 
public class DescMap implements Comparator<String>{ 
    public int compare(String o1, String o2) {         
        int map1 = Integer.parseInt(o1);         
        int map2 = Integer.parseInt(o2);         
        return map2-map1; 
    } 
    public static void main(String[] args) {         
        String[] arraySources = {"1","2","3","0"};         
        int[] arrayValue = {1,424,32,123};         
        Map mapCurrentWebSite = new TreeMap(new DescMap());         
        
        for(int i=0;i<arraySources.length;i++) {               
            mapCurrentWebSite.put(arraySources[i],new Integer(arrayValue[i]));          
        }         
        
        Collection col = mapCurrentWebSite.values();         
        Vector v1 = new Vector(col);         
        
        for(int i=0;i<v1.size();i++) {
            System.out.println((Integer)v1.get(i));   
        } 
    } 
}



© 著作权归作者所有

共有 人打赏支持
陶邦仁
粉丝 1587
博文 420
码字总数 1483822
作品 0
海淀
技术主管
大数据开发培训:0基础学习Java编程语言有哪些知识点?

Java 技术通用、高效、具有平台移植性和安全性,广泛应用于PC、数据中心、游戏控制台、科学超级计算机、移动电话和互联网等,学习Java首先要知道学习知识点有哪些。在这就用加米谷大数据培训...

加米谷大数据
07/25
0
0
一份关于 Java、Kotlin 与 Android 的学习笔记

JavaKotlinAndroidLearn 这是一份关于 Java 、Kotlin 、Android 的学习笔记,既包含对基础知识点的介绍,也包含对一些重要知识点的源码解析,笔记的大纲如下所示: Java 重拾Java(0)-基础知...

叶应是叶
08/08
0
0
【目录导航】JAVA零基础进阶之路

【JAVA零基础入门系列】(已完结)导航目录 Day1 开发环境搭建 Day2 Java集成开发环境IDEA Day3 Java基本数据类型 Day4 变量与常量 Day5 Java中的运算符 Day6 Java字符串 Day7 Java输入与输出...

MFrank
06/21
0
0
java web开发中Filter使用Annotation配置 (转载)

为了在java中得到request和response对象,搜索到了 《如何在Java的普通类中获取Session以及request对象 》这篇日志,当写完Filter后,却忘了如何配置Filter,于是又搜索到 《Java Web开发中F...

hiqj
2014/03/20
0
0
【Java并发专题】27篇文章详细总结Java并发基础知识

努力的意义,就是,在以后的日子里,放眼望去全是自己喜欢的人和事! github:https://github.com/CL0610/Java-concurrency,欢迎题issue和Pull request。所有的文档都是自己亲自码的,如果觉...

你听___
05/06
0
0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

windbg调试C源码级驱动

联机方式不多说了。我博客里有,英文的。 windbg联机文档 https://docs.microsoft.com/zh-cn/windows-hardware/drivers/debugger/debug-universal-drivers---step-by-step-lab--echo-kernel......

simpower
38分钟前
0
0
redis快照和AOF简介

数据持久化到硬盘:一是快照(snapshotting),二是只追加文件(append-only file AOF) 快照 核心原理:redis某个时间内存内的所有数据写入硬盘 场景:redis快照内存里面的数据 1. 用户发送bgsav...

拐美人
38分钟前
0
0
这个七夕,送你一份程序员教科书级别的告白指南

给广大爱码士们的高能预警: 今天,就是七夕了…… (单身非作战人群请速速退场!) 时常有技术GG向个推君抱怨 经过网民多年的教育 以及技术人持之以恒的自黑 冲锋衣狂热分子·格子衫骨灰级粉...

个推
43分钟前
0
0
python爬虫日志(15)cookie详解

转载:原文地址 早期Web开发面临的最大问题之一是如何管理状态。服务器端没有办法知道两个请求是否来自于同一个浏览器。那时的办法是在请求的页面中插入一个token,并且在下一次请求中将这个...

茫羽行
44分钟前
0
0
qlv视频格式转换器

  腾讯视频中的视频影视资源有很多,小编经常在里面下载视频观看,应该也有很多朋友和小编一样吧,最近热播的电视剧也不少,如《香蜜沉沉烬如霜》、《夜天子》还有已经完结的《扶摇》,这么...

萤火的萤火
48分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

返回顶部
顶部