美文网首页Java学习
黑马程序员-集合框架

黑马程序员-集合框架

作者: 狼孩 | 来源:发表于2015-04-14 18:35 被阅读120次

    -------android培训java培训期待与您交流!----------

    介绍
    • 出现的原因:面向对象语言对事物的体现都是以对象的形式存在,为了方便对多个对象的操作,就对对象进行存储,集合就是存储对象最常用的一种方式。集合就是将若干用途、性质相同或相近的"数组"组合而成一个整体。
    • 数组和集合的不同:数组可以存储对象,但长度是固定的;集合长度是可变的。数组中可以存储基本数据类型,集合只能存储对象。
    • 集合的特点:集合只用于存储对象,集合长度是可变,集合可以存粗不同类型的对象。
    集合体系结构图
    • 根据数据结构的不同,集合可以分为以下结构体系:


      集合框架.png
    Collection接口和迭代器
    • 提供List、Set等数据结构集合的最基础共性的方法接口。
    • 迭代器:集合的取出元素的方式。

    实现为:每个数据结构不同的集合取出方式定义在内部,取出方式被定义成了内部类,所以取出的方式也不一样,但是都有共性方式:判断和取出,可以抽取共性。而这些内部类都可以抽取成Iterator接口特性规则,对外提供iterator();方法取出元素。

    package com.sergio.Collections;
    
    import java.util.ArrayList;
    import java.util.Collection;
    import java.util.Iterator;
    
    /**
     * collection接口介绍接迭代器介绍
     * Created by Sergio on 2015/1/16.
     */
    public class CollectionDemo {
        public static void main(String[] args) {
            sop(-1 % 2);
    
        }
    
        public static void sop(Object obj) {
            System.out.println(obj);
        }
    
        //集合元素交集方法
        public static void CollectionRetainAllMethod() {
            //创建一个集合容器,使用Collection接口的子类ArrayList演示共性方法
            Collection al1 = new ArrayList();
            al1.add("hello1");
            al1.add("hello2");
            al1.add("hello3");
            al1.add("hello4");
    
            ArrayList al2 = new ArrayList();
            al2.add("hello1");
            al2.add("hello2");
            al2.add("hello5");
            al2.add("hello7");
    
            al1.retainAll(al2); //取交集,al中保留和al1相同的元素
            al1.retainAll(al2); //删除al中al1存在的元素
        }
    
        //collection集合基础方法使用介绍
        public static void CollectionMethod() {
            //创建一个集合容器,使用Collection接口的子类ArrayList演示共性方法
            Collection al = new ArrayList();
    
            /**
             * 添加元素
             * 1. add方法的参数类型是Object,以便于接受任意类型对象
             * 2. 集合中存储的都是对象的引用(地址)
             */
            al.add("hello1");
            al.add("hello2");
            al.add("hello3");
            al.add("hello4");
    
            //打印原集合
            sop(al);
    
            //获取集合长度
            sop("长度:" + al.size());
    
            //删除元素
            al.remove("hello2");
            //打印删除后的集合
            sop(al);
            al.clear(); //清空集合
    
            //判断元素
            sop("hello3" + al.contains("hello3")); //是否包含hello3元素
            sop(al.isEmpty()); //是否为空
        }
    
        //获取集合中的元素.迭代器介绍
        public static void CollectionGet() {
            Collection al = new ArrayList();
            al.add("hello1");
            al.add("hello2");
            al.add("hello3");
            al.add("hello4");
    
            Iterator it = al.iterator();//获取迭代器,用于取出集合中的元素
            while (it.hasNext()) {
                sop(it.next());
            }
            //此方法相对while循环的效果一样。但是比while节省内存空间,for循环完就释放了内存,而while没有。推荐使用此方法
            //        for(Iterator it = al.iterator(); it.hasNext();)
            //        {
            //            sop(it.next());
            //        }
        }
    }
    
    List
    • 元素是有序的,元素可以重复。因为该集合体系有索引。
    • 特有方法:凡是可以操作角标的方法都是该体系特有的方法。
    • List特有的迭代器ListIterator:ListIterator是Iterator的子接口。在迭代器时,不可以通过集合对象的方法操作集合中的元素,因为会发生ConcurrentModificationException异常。因为,在迭代器时,只能用迭代器的方式操作元素,可是Iterator方式有限的,只能对元素进行判断,取出,删除的操作,如果想要其他的操作如添加,修改等,就需要使用其子接口ListIterator。 该接口之能通过List的集合的listIterator方法获取。因为list都带有角标。
    package com.sergio.Collections;
    
    import java.util.ArrayList;
    import java.util.Iterator;
    import java.util.List;
    import java.util.ListIterator;
    
    /**
     * Created by Sergio on 2015/1/19.
     */
    public class ListDemo1 {
        public static void main(String[] args) {
            List al = new ArrayList();
    
            al.add("hello1");
            al.add("hello2");
            al.add("hello3");
            al.add("hello4");
    
            sop("原集合是:" + al);
    
            al.add(1, "hello8"); //在指定位置插入元素,后面元素依次后移,容量增加1
    
            al.remove(2); //删除指定位置的元素
    
            al.set(2, "hell5"); //修改指定位置的元素
    
            al.get(3); //通过角标获取元素
    
            //获取集合所有元素
            for (int x = 0; x < al.size(); x++) {
                System.out.println("al(" + x + " +)" + al.get(x));
            }
            //迭代器获取元素
            Iterator it = al.iterator();
            while (it.hasNext()) {
                sop("next:" + it.next());
            }
    
            sop(al.indexOf("hello3")); //通过indexOf获取对象的位置
    
            List sub = al.subList(1, 3); //截取列表元素,包含头,不包含尾
            sop(al);
            
            listIterator();
        }
    
        /**
         * List集合特有的迭代器。ListIterator是Iterator的子接口。
         * 在迭代器时,不可以通过集合对象的方法操作集合中的元素,因为会发生ConcurrentModificationException异常。
         * 因为,在迭代器时,只能用迭代器的方式操作元素,可是Iterator方式有限的,只能对元素进行判断,取出,删除的操作,
         * 如果想要其他的操作如添加,修改等,就需要使用其子接口ListIterator。
         * <p>
         * 该接口之能通过List的集合的listIterator方法获取。因为list都带有角标.
         */
        public static void listIterator() {
            List al = new ArrayList();
    
            al.add("hello1");
            al.add("hello2");
            al.add("hello3");
            al.add("hello4");
    
            sop(al);
    
            //在循环中操作元素
            ListIterator li = al.listIterator();
            //正向获取元素。
            while (li.hasNext()) {
                Object obj = li.next();
                if (obj.equals("hello3")) {
                    li.add("hello6");//添加
                    li.set("hello4");//修改
                }
            }
    
            //反向获取元素
            while (li.hasPrevious()) {
                sop("pre: " + li.hasPrevious());
            }
            sop(al);
            //        //在迭代过程中,准备添加或删除元素。在迭代器中只能使用迭代器的方法,
            //        // 集合对象引用中只能使用集合的方法,集合和迭代器有两个相同对象引用,所以修改一方时会引发安全异常。
            //        Iterator it = al.iterator();
            //        while (it.hasNext())
            //        {
            //            Object obj = it.next();
            //            if(obj.equals("hello2"))
            //            {
            //                it.remove(); //将hello3的引用从集合中删除
            //            }
            //            sop("obj=" + obj);
            //        }
        }
    
        public static void sop(Object obj) {
            System.out.println(obj);
        }
    }
    
    • List常见的子类对象:
    1. ArrayList:底层的数据结构使用的是数组结构。特点:查询更改速度快,增删稍慢。线程不同步。可变长度数组:元素初始是10的元素空间,超过10空间,按原数组的50%增加空间,也就是变成15,new一个新的数组,将原始空间中的元素复制进来和新增加的元素添加到后面的空间中。
    2. LinkedList:底层使用的是链表数据结构。特点:查询满,增删快。
    3. Vector:底层是数组数据结构。特点:查询、增删满。线程同步。可变长度数组:元素初始是10的元素空间,超过10空间,按原数组的50%增加空间,也就是变成15,new一个新的数组,将原始空间中的元素复制进来和新增加的元素添加到后面的空间中。
    • Vector:枚举是Vector特有的取出方式,枚举和迭代器重复。枚举的名称和方法名称过长,被迭代器取代了。
    package com.sergio.Collections;
    
    import java.util.Enumeration;
    import java.util.Vector;
    
    /**
     * Vector枚举获取元素
     * Created by Sergio on 2015/1/19.
     */
    public class VectorDemo {
        public static void main(String[] args) {
            Vector v = new Vector();
            v.add("hello1");
            v.add("hello2");
            v.add("hello3");
            v.add("hello4");
    
            //和迭代器重复
            Enumeration en = v.elements();
            while (en.hasMoreElements())
            {
                System.out.println(en.nextElement());
            }
        }
    }
    
    • LinkedList:链表数据结构的,元素之间的联系是上个元素中保存着下个元素的位置信息,每个元素是这样联系的,所以查询满,删除块只需要改变相邻两个元素之间的位置指向的信息即可。
    package com.sergio.Collections;
    
    import java.util.LinkedList;
    
    /**
     * LinkedList实现中特有的方法介绍
     * Created by Sergio on 2015/1/19.
     */
    public class LinkedDemo {
        public static void main(String[] args) {
            LinkedList lk = new LinkedList<>();
            lk.addFirst("hello1");
            lk.addFirst("hello2");
            lk.addFirst("hello3");
            lk.addFirst("hello4");
    
            sop(lk); //打印的顺序是倒着放置元素的
    
            //此下集中删除获取元素时,如果集合中没有元素,会出现NoSuchElementsException
            //在Jdk1.6出现了替代方案:
            //增加:offerFist(),offerLast();获取元素不删除(如果没有元素会返回null):peekFirst(),peekLast();获取元素并删除(如果没有元素会返回null):pollFist(),pollLast().
            sop(lk.removeFirst()); //获取第一个元素并删除
            sop(lk.removeFirst()); //获取最后一个元素并删除
            sop(lk.getFirst()); //获取第一个元素,不删除元素
            sop(lk.getLast()); //获取最后一个元素,不删除元素
    
            //获取集合中所有元素
            while (lk.isEmpty()) {
                sop(lk.getLast());
            }
            sop(lk.size());
        }
    
        public static void sop(Object obj)
        {
            System.out.println(obj);
        }
    }
    
    package com.sergio.Collections;
    
    import java.util.LinkedList;
    
    /**
     * LinkedList模拟一个堆栈或者队列数据结构
     * 堆栈:先进后出。
     * 队列:先进先出。
     * Created by Sergio on 2015/1/19.
     */
    public class LinkedDemo2 {
        public static void main(String[] args) {
            Queue q = new Queue();
            q.myAdd("hello1");
            q.myAdd("hello2");
            q.myAdd("hello3");
            q.myAdd("hello4");
            //获取所有元素
            while (!q.isNull()) {
                System.out.println(q.myGet());
            }
    
            Stack s = new Stack();
            s.myAdd("hello1");
            s.myAdd("hello2");
            s.myAdd("hello3");
            //获取所有元素
            while (!s.isNull()) {
                System.out.println(s.myGet());
            }
        }
    }
    
    
    //队列.根据队列特点,利用LinkedList封装一些功能。
    class Queue {
        private LinkedList link;
    
        Queue() {
            link = new LinkedList();
        }
    
        //在第一个位置添加元素,先进
        public void myAdd(Object obj) {
            link.addFirst(obj);
        }
    
        //获取第一个进入的元素,先出
        public Object myGet() {
            return link.removeLast();
        }
    
        //判断元素是否为空
        public boolean isNull() {
            return link.isEmpty();
        }
    }
    
    
    //堆栈,封装成一些功能
    class Stack {
        private LinkedList link;
    
        Stack() {
            link = new LinkedList();
        }
    
        //在第一个位置添加元素,先进
        public void myAdd(Object obj) {
            link.addFirst(obj);
        }
    
        //获取最后一个进入的元素,后出
        public Object myGet() {
            return link.removeLast();
        }
    
        //判断元素是否为空
        public boolean isNull() {
            return link.isEmpty();
        }
    }
    
    Set
    • 元素是无序(存入和取出的元素顺序不一定一致)的,元素不可以重复。
    • Set和Collection的功能是一致的。
    • Set常见子类对象:
    1.HashSet:底层的数据结构是哈希表。线程不同步。
      * 保证唯一性:是通过元素的两个方法,hashCode和equals来完成。如果元素的HashCode值相同,才会判断equals是否为true。如果元素的HashCode值不同,才会调用equals。
      * 注意:对于判断元素是否存在,以及删除等操作,依赖方法是元素的hashCode和equals方法。
    
    package com.sergio.Collections;
    
    import java.util.HashSet;
    import java.util.Iterator;
    import java.util.Set;
    
    /**
     * HashSet的添加、删除等元素使用介绍。跟Collection一致的用法。
     * Created by Sergio on 2015/1/20.
     */
    public class HashSetDemo {
        public static void main(String[] args) {
            Set hs = new HashSet<>();
            //存person2的对象元素
            hs.add(new Person2("hello1", 11));
            hs.add(new Person2("hello3", 12));
            hs.add(new Person2("hello2", 31));
            hs.add(new Person2("hello1", 11));
    
            sop(hs.contains(new Person2("hello1", 11))); //判断新对象是否在集合中存在
            hs.remove(new Person2("hello2", 12)); //删除集合中跟新对象一样的元素
    
            Iterator it = hs.iterator();
            while (it.hasNext()) {
                Person2 p = (Person2) it.next();
                sop(p.getName() + "::" + p.getAge());
            }
        }
    
        public static void sop(Object obj) {
            System.out.println(obj);
        }
    }
    
    
    //存储的对象
    class Person2 {
        private String name;
        private int age;
    
        Person2(String name, int age) {
            this.name = name;
            this.age = age;
        }
    
        //比较两者对象的地址值
        @Override
        public boolean equals(Object o) {
            if (this == o) {
                return true;
            }
            if (!(o instanceof Person2)) {
                return false;
            }
    
            Person2 p = (Person2) o;
            return this.name.equals(p.name) && this.age == p.age;
        }
    
        //返回字符串的哈希值
        @Override
        public int hashCode() {
            int result = name.hashCode();
            result = 31 * result + age;
            return result;
        }
    
        public int getAge() {
            return age;
        }
    
        public void setAge(int age) {
            this.age = age;
        }
    
        public String getName() {
    
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    }
    
    2.TreeSet
    • 可以对Set集合中的元素进行排序。默认按照自然顺序排序。
    • 排序时:当主要条件相同时,一定要判断下次要条件。
    • 底层数据结构是:二叉树。保证数据唯一性的依据:compareTo方法return 大于(1),等于(0),小于(-1)。
    1. TreeSet排序的第一种方式:让元素自身具备比较性。元素需要实现Comparable接口,覆盖compareTo方法,这种方式也称为元素的自然顺序,或者默认字典顺序。
    2. TreeSet的第二种排序方式:当元素自身不具备比较性,或者具备的比较性不是所需要的。这时需要让集合自身具备比较性。在集合初始化时,就让其具备比较性,也就是构造函数指定比较器。两种排序都存在时,以比较器为主。定义一个类,实现comparator接口,覆盖compare方法。
    1. TreeSet使用介绍:
    package com.sergio.Collections;
    
    import java.util.Iterator;
    import java.util.Set;
    import java.util.TreeSet;
    
    /**
     * TreeSet使用介绍及比较器方法介绍。
     * Created by Sergio on 2015/1/20.
     */
    public class TreeSetDemo {
        public static void main(String[] args) {
            Set ts = new TreeSet();
    
            ts.add(new Student("hello1", 30));
            ts.add(new Student("hello2", 30));
            ts.add(new Student("hello3", 40));
    
            Iterator it = ts.iterator();
            while (it.hasNext()) {
                Student stu = (Student) it.next();
                System.out.println(stu.getName() + stu.getAge());
            }
    
        }
    }
    
    //此接口让学生类具有比较性
    class Student implements Comparable {
        private String name;
        private int age;
    
        Student(String name, int age) {
            this.name = name;
            this.age = age;
        }
    
        public int getAge() {
            return age;
        }
    
        public void setAge(int age) {
            this.age = age;
        }
    
        public String getName() {
    
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    
        //按学生年龄大小排序
        @Override
        public int compareTo(Object o) {
            if (!(o instanceof Student)) {
                throw new RuntimeException("不是学生对象");
            }
            //排序判断条件
            Student stu = (Student) o;
            //树的左边
            if (this.age > stu.age) {
                return 1;
            }
            //相等时,比较次要条件进行排序
            if (this.age == stu.age) {
                return this.name.compareTo(stu.name);
            }
            //树的右边
            return -1;
        }
    }
    
    1. TreeSet第一种元素可以比较方法介绍:
    package com.sergio.Collections;
    
    import java.util.Comparator;
    import java.util.Iterator;
    import java.util.Set;
    import java.util.TreeSet;
    
    /**
     * 比较器创建方式,自定义比较器类,实现comparator接口。
     * Created by Sergio on 2015/1/20.
     */
    public class TreeSetDemo2 {
        public static void main(String[] args) {
            Set ts = new TreeSet(new MyCompare());
    
            ts.add(new Teacher("hello1", 30));
            ts.add(new Teacher("hello2", 20));
            ts.add(new Teacher("hello3", 50));
            ts.add(new Teacher("hello2", 70));
            ts.add(new Teacher("hello2", 40));
    
            Iterator it = ts.iterator();
            while (it.hasNext()) {
                Teacher stu = (Teacher) it.next();
                System.out.println(stu.getName() + "::" + stu.getAge());
            }
        }
    }
    
    
    //此接口让学生类具有比较性
    class Teacher implements Comparable {
        private String name;
        private int age;
    
        Teacher(String name, int age) {
            this.name = name;
            this.age = age;
        }
    
        public int getAge() {
            return age;
        }
    
        public void setAge(int age) {
            this.age = age;
        }
    
        public String getName() {
    
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    
        //按年龄大小排序
        @Override
        public int compareTo(Object o) {
            if (!(o instanceof Teacher)) {
                throw new RuntimeException("不是学生对象");
            }
            //排序判断条件
            Teacher stu = (Teacher) o;
            //树的左边
            if (this.age > stu.age) {
                return 1;
            }
            //相等时,比较次要条件进行排序
            if (this.age == stu.age) {
                return this.name.compareTo(stu.name);
            }
            //树的右边
            return -1;
        }
    }
    
    
    //自定义比较器,实现Comparator接口中的compare方法。按姓名字幕顺序自然排序
    class MyCompare implements Comparator {
        public int compare(Object o1, Object o2) {
            Teacher s1 = (Teacher) o1;
            Teacher s2 = (Teacher) o2;
    
            int num = s1.getName().compareTo(s2.getName());
            if (num == 0) {
                return new Integer(s1.getAge()).compareTo(new Integer(s2.getAge()));
                //等价上一句
                //            if (s1.getAge() > s2.getAge())
                //                return 1;
                //            if (s1.getAge() == s2.getAge())
                //                return 0;
                //            return -1;
            }
            return num;
        }
    }
    
    1. TreeSet练习(包括内部类使用方式介绍)
    package com.sergio.Collections;
    
    import java.util.Comparator;
    import java.util.Iterator;
    import java.util.Set;
    import java.util.TreeSet;
    
    /**
     * 按字符串长度排序.比较方式微分:创建比较类和创建比较匿名函数
     * Created by Sergio on 2015/1/21.
     */
    public class TreeSetDemo3 {
        public static void main(String[] args) {
            Set ts = new TreeSet(new Comparator() {
                @Override
                public int compare(Object o1, Object o2) {
                    String s1 = (String) o1;
                    String s2 = (String) o2;
    
                    int num = new Integer(s1.length()).compareTo(new Integer(s2.length()));
                    //主要条件比完,需要比较次要条件,防止重复元素
                    if (num == 0) {
                        return s1.compareTo(s2);
                    }
                    return num;
                }
            });
    
            ts.add("a");
            ts.add("sff");
            ts.add("sdfsfsf");
            ts.add("sgdggse");
    
            Iterator it = ts.iterator();
            while (it.hasNext())
    
            {
                System.out.println(it.next());
            }
        }
    }
    
    //比较字符串长度
    //class StringLenCompare implements Comparator {
    //    public int compare(Object o1, Object o2) {
    //        String s1 = (String) o1;
    //        String s2 = (String) o2;
    //
    //        int num = new Integer(s1.length()).compareTo(new Integer(s2.length()));
    //        //主要条件比完,需要比较次要条件,防止重复元素
    //        if (num == 0) {
    //            return s1.compareTo(s2);
    //        }
    //        return num;
    //    }
    //}
    
    Map
    • Map框架图:
    Map结构图.png
    • Map<K,V>:K--此映射所维护的键的类型;V--映射值的类型。

    • Map集合存储键值对,一对一对存取,而且要保证键的唯一性。

    • Hashtable:底层是哈希表数据结构,不可以存入null键null值。该集合是线程同步的。效率低。

    • HashMap:底层是哈希表数据结构,允许使用null键null值,该集合是不同步的。效率高。

    • TreeMap:底层是二叉树数据结构,线程不同步。可以用于Map集合中键进行排序。
      Set集合的底层使用了Map集合功能。

    package com.sergio.Collections;
    
    import java.util.Collection;
    import java.util.HashMap;
    import java.util.Map;
    
    /**
     * Created by Sergio on 2015/1/22.
     */
    public class MapIntroduction {
        public static void main(String[] args) {
            Map<String, String> map = new HashMap<String, String>();
            //添加元素,当存入键时相同时,存入的新值会覆盖原来的值。当存入键时相同时,put会返回原来键所对应的值。
            map.put("01", "yiyi");
            map.put("01", "lier");
            map.put("03", "lisi");
    
            sop(map.containsKey("02")); //是否包含键为02的值
            sop(map.remove("02")); //根据键删映射值
    
            sop(map.get("01")); //根据键获取映射值.也可以通过get方法的返回值判断一个键是否存在,通过返回null判断
    
            Collection<String> coll = map.values();
            sop(coll); //获取mao集合中所有的值
        }
    
        public static void sop(Object obj) {
            System.out.println(obj);
        }
    }
    
    • Map中另外两种获取元素的方式:
    1. keySet:将Map中所有的键存入到Set集合,而Set集合具有迭代器功能,可以通过此方式获取所有的键,再根据get方法,获取每一个键对应的值。
    2. Set<Map.Entry<k,v>> entry:将Map集合中的映射关系存入到了Set集合中,而这个关系的数据类型是:Map.Entry。Map.Entry的关系具体实现是:Entry做为Map接口的内部接口存在,其中包含getKey和getValue的方法,通过这两种方法可以获取键和值。
    package com.sergio.Collections;
    
    import java.util.HashMap;
    import java.util.Iterator;
    import java.util.Map;
    import java.util.Set;
    
    /**
     * Map集合中的两种获取元素方式
     * Created by Sergio on 2015/1/22.
     */
    public class MapGetSet {
        public static void main(String[] args) {
            Map<String, String> map = new HashMap<String, String>();
            map.put("01", "yiyi");
            map.put("02", "lier");
            map.put("03", "lisi");
            //将Map集合中的映射关系取出,存入到Set集合中.这种关系类型为Map.Entry。
            //再通过Map.Entry关系接口中定义的方法getKey和getValue获取关系中的键和值
            Set<Map.Entry<String, String>> entrySet = map.entrySet();
            Iterator<Map.Entry<String, String>> it = entrySet.iterator();
            while (it.hasNext())
            {
                Map.Entry<String, String> me = it.next();
                String key = me.getKey();
                String values = me.getValue();
    
                System.out.println(key + ":"+ values);
            }
    
            //先获取mao集合的所有键的Set集合,keySet
            Set<String> keySet = map.keySet();
            //根据Set集合,获取迭代器
            Iterator<String> it1 = keySet.iterator();
            while(it1.hasNext())
            {
                String key = it1.next();
                //结果为key的结果集
                String values = map.get(key);
                System.out.println("key: " + key + "values" + values);
            }
        }
    }
    

    练习:

    package com.sergio.Collections;
    
    import java.util.HashMap;
    import java.util.Iterator;
    import java.util.Map;
    import java.util.Set;
    
    /**
     * HashMap练习:公民信息有姓名、年龄、住址。用HashMap存储公民信息,姓名、年龄相同被视为同一个公民。公民年龄具有自然比较。
     * Created by Sergio on 2015/1/22.
     */
    public class HashMapTest {
        public static void main(String[] args) {
            Map<Citizen, String> hm = new HashMap<Citizen, String>();
            hm.put(new Citizen("lisi", 23), "chengdu");
            hm.put(new Citizen("haili", 34), "xian");
            hm.put(new Citizen("wangi", 53), "beijing");
    
            Set<Citizen> set = hm.keySet();
            Iterator<Citizen> it = set.iterator();
            while (it.hasNext()) {
                Citizen ct = it.next();
                String str = hm.get(ct);
                System.out.println(ct + str);
            }
        }
    }
    
    
    class Citizen implements Comparable<Citizen> {
        private String name;
        private int age;
    
        Citizen(String name, int age) {
            this.name = name;
            this.age = age;
        }
    
        public int getAge() {
            return age;
        }
    
        public void setAge(int age) {
            this.age = age;
        }
    
        public String getName() {
    
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    
        public int compareTo(Citizen s) {
            int num = new Integer(this.age).compareTo(s.getAge());
            if (num == 0) {
                return this.name.compareTo(s.getName());
            }
            return num;
        }
    
        public int hashCode() {
            return name.hashCode() + age * 34;
        }
    
        public boolean equals(Object obj) {
            //        if (this == obj) {
            //            return true;
            //        }
            if (!(obj instanceof Citizen)) {
                throw new ClassCastException("输入类型与公民类型不匹配");
            }
            Citizen s = (Citizen) obj;
            return this.name.equals(s.getName()) && this.age == s.getAge();
        }
    
        @Override
        public String toString() {
            return "Citizen{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
        }
    }
    
    package com.sergio.Collections;
    
    import java.util.*;
    
    /**
     * TreeMap练习,创建比较器类,让公民的名字具有比较器。
     * Created by Sergio on 2015/1/23.
     */
    public class TreeMapTest {
        public static void main(String[] args) {
            Map<Citizen, String> hc = new TreeMap<Citizen, String>(new MyCompareTo());
            hc.put(new Citizen("abc", 23), "beijing");
            hc.put(new Citizen("wabc", 33), "shanghai");
            hc.put(new Citizen("sabc", 43), "chengdu");
    
            Set<Map.Entry<Citizen, String>> tm = hc.entrySet();
    
            Iterator<Map.Entry<Citizen, String>> it = tm.iterator();
            while (it.hasNext()) {
                Map.Entry<Citizen, String> me = it.next();
                Citizen cname = me.getKey();
                String add = me.getValue();
                System.out.println(cname + add);
            }
        }
    }
    
    //自定义比较器类
    class MyCompareTo implements Comparator<Citizen> {
        @Override
        public int compare(Citizen o1, Citizen o2) {
            int num = o1.getName().compareTo(o2.getName());
            if (num == 0) {
                return new Integer(o1.getAge()).compareTo(o2.getAge());
            }
            return num;
        }
    }
    
    package com.sergio.Collections;
    
    import java.util.ArrayList;
    import java.util.HashMap;
    import java.util.Iterator;
    import java.util.List;
    
    /**
     * 集合嵌套练习
     * Created by Sergio on 2015/2/11.
     */
    public class CollectionInCollection {
        public static void main(String[] args) {
            demo();
        }
    
        //参考集合嵌套书写
        public static void demo() {
            HashMap<String, List<Car>> jhqt = new HashMap<>();
            List<Car> jc = new ArrayList<Car>();
            List<Car> pc = new ArrayList<Car>();
    
            jhqt.put("轿车", jc);
            jhqt.put("跑车", pc);
    
            jc.add(new Car("0111", "zhangsa"));
            jc.add(new Car("023444", "lisi"));
            pc.add(new Car("0234", "wangwu"));
            pc.add(new Car("01234", "maliu"));
            //迭代器获取车信息
            Iterator<String> it = jhqt.keySet().iterator();
            while (it.hasNext()) {
                String carName = it.next();
                List<Car> name = jhqt.get(carName);
    
                System.out.println(carName);
                getInfo(name);
            }
        }
    
        //获取list集合中的信息
        public static void getInfo(List<Car> list) {
            Iterator<Car> it = list.iterator();
            while (it.hasNext()) {
                Car c = it.next();
                System.out.println(c);
            }
        }
    
        //获取嵌套集合中车信息方式
    //    public static void getCarInfo(HashMap<String, String> carMap) {
    //        Iterator<String> it = carMap.keySet().iterator();
    //        while (it.hasNext()) {
    //            String id = it.next();
    //            String name = carMap.get(id);
    //            System.out.println(id + "::::" + name);
    //        }
    //    }
    }
    
    
    class Car {
        private String id;
        private String name;
    
        Car(String id, String name) {
            this.id = id;
            this.name = name;
        }
    
        public String toString() {
            return id + ":::::" + name;
        }
    }
    
    Collections工具类
    • 此工具类中的方法定义的都是静态方法,共享性数据,没有提供构造函数。
    • public static <T extends [Comparable<? super T>> void sort([List<T> list):集合工具类中的List集合排序方法,<T extends [Comparable<? super T>>表示类型限定是Comparable的子类,接受的类型是子类或者子类的父类。
    • Collection和Collections的区别:
    1. Collection是集合框架的一个顶层接口,定义了单列集合的共性方法,两个重要的子接口List(对元素都有定义索引。有序,元素可重复)、Set(元素不重复,无序)。
    2. Colections是集合框架中的一个工具类,该类的方法都是静态的,提供对list等集合进行排序,二分查找等方法,通常常用的集合都是线程不安全的,当多线程操作这些集合时,可以使用该工具类将线程不安全的集合转换成安全同步的。
    package com.sergio.CollectionsUtils;
    
    import java.util.ArrayList;
    import java.util.Collections;
    import java.util.Comparator;
    import java.util.List;
    
    /**
     * 工具类使用。排序方法介绍
     * Created by Sergio on 2015-02-23.
     */
    public class IntroductionCollections {
        public static void main(String[] args) {
            sortDemo();
            maxDemo();
            fillDem();
            reverseDemo();
        }
    
        //排序
        public static void sortDemo() {
            List<String> list = new ArrayList<>();
    
            list.add("absdf");
            list.add("bsdfdf");
            list.add("osdf");
    
            sop(list);
            //工具类排序,数组实现的重复元素排序按索引排序
            Collections.sort(list);
            ////工具类排序.自定义比较器
            Collections.sort(list, new StrLenComparator());
            sop(list);
        }
    
        //求最大值.
        public static void maxDemo() {
            List<String> list = new ArrayList<>();
    
            list.add("absdf");
            list.add("bsdfdf");
            list.add("osdf");
            list.add("zzz");
    
    
            sop(list);
            //按自然排序求最大值
            String max2 = Collections.max(list);
            //自定义比较器排序求最大值
            String max = Collections.max(list, new StrLenComparator());
            sop(max);
            sop(max2);
        }
    
        //二分查找.集合必须是有序的
        public static void binarySearchDemo() {
            List<String> list = new ArrayList<>();
    
            list.add("absdf");
            list.add("bsdfdf");
            list.add("osdf");
            list.add("zzz");
            //先进性排序
            Collections.sort(list);
    
            sop(list);
            int index = Collections.binarySearch(list, "zzz");
            sop("index " + index);
        }
    
        //将集合中的元素全部替换成指定元素
        public static void fillDem() {
            List<String> list = new ArrayList<>();
    
            list.add("absdf");
            list.add("bsdfdf");
            list.add("osdf");
            list.add("zzz");
    
            sop(list);
            Collections.fill(list, "ppp");
            sop(list);
        }
    
        //替换指定区间的元素
        public static void fillDemo2(List<String> list, int start, int end, String str) {
            List<String> list1 = new ArrayList<>();
    
            list1.add("absdf");
            list1.add("bsdfdf");
            list1.add("osdf");
            list1.add("zzz");
    
            List<String> subList = list.subList(start, end);
            Collections.fill(subList, str);
            sop(list);
        }
    
        //反转集合元素
        public static void reverseDemo() {
            List<String> list = new ArrayList<>();
            list.add("sdf");
            list.add("sdfsdf");
            list.add("weri");
    
            Collections.reverse(list);
            sop(list);
        }
    
        public static void sop(Object obj) {
            System.out.println(obj);
        }
    }
    
    
    //自定义比较器
    class StrLenComparator implements Comparator<String> {
        public int compare(String s1, String s2) {
            if (s1.length() > s2.length()) {
                return 1;
            }
            if (s1.length() < s2.length()) {
                return -1;
            }
            return s1.compareTo(s2);
        }
    }
    
    Arrays工具类
    package com.sergio.Arrays;
    
    import java.util.Arrays;
    import java.util.List;
    
    /**
     * 数组变集合
     * Created by Sergio on 2015-02-23.
     */
    public class ArrayToCollection{
        public static void main(String[] args) {
            String[] str = {"1", "2", "5"};
    
            /**
             * 将数组变成list集合:
             * 变成list集合后可以使用集合的思想和方法来操作数组中的元素。
             * 注意:不可以使用集合的增删方法。因为数组的长度是固定的。
             */
            List<String> list = Arrays.asList(str);
            System.out.println("包含:" + list.contains("4"));
            System.out.println(list);
    
            /**
             * 如果数组中的元素都是对象,那么变成集合时,数组中的元素就直接转换成集合中的元素。
             * 如果数组中的元素都是基础数据类型,那么会将数组作为集合中的元素存在。
             */
            int[] num = {1, 2, 6};
            List<int[]> li = Arrays.asList(num);
            System.out.println(li);
    
        }
    }
    
    package com.sergio.Arrays;
    
    import java.util.ArrayList;
    import java.util.Arrays;
    
    /**
     * 集合转数组.当集合元素数限定,转成数组不可操作增删操作,非常有用
     * Created by Sergio on 2015-02-23.
     */
    public class CollectionToArray {
        public static void main(String[] args) {
            ArrayList<String> al = new ArrayList<>();
            al.add("acb1");
            al.add("abc2");
            al.add("abc3");
            //数组的大小为集合元素的空间大小
            String[] arr = al.toArray(new String[al.size()]);
            System.out.println(Arrays.toString(arr));
        }
    }
    

    相关文章

      网友评论

        本文标题:黑马程序员-集合框架

        本文链接:https://www.haomeiwen.com/subject/auscxttx.html