黑马程序员---集合(一)



------<a href="http://www.itheima.com" target="blank">Java培训、Android培训、iOS培训、.Net培训</a>、期待与您交流! -------

集合框架

(1)为什么出现集合类?

        面向对象对事物的体现都是以对象的形式,为了方便对多个对象的操作,就对对象进行存储。集合就是存储对象最常用的一种方式.

    (2)数组和集合都是容器,两者有何不同?

        数组长度固定,而集合长度是可变的 

        数组值可以存储对象,还可以存储基本数据类型;而集合只能存储对象

        数组存储数据类型是固定的,而集合存储的数据类型不固定(要固定需要加泛型)

集合类框架:

        Collection:顶层接口

             |--->List:列表,元素是有序的(元素带角标索引),可以有重复元素,可以有null元素。

                |--->ArrayList(JDK1.2):底层的数据结构是数组数据结构,特点是查询速度快(因为带角标),

                           但是增删速度稍慢,因为当元素多时,增删一个元素则所有元素的角标都得改变

                           线程不同步。默认长度是10,当超过长度时,按50%延长集合长度。               

                |--->LinkedList(JDK1.2):底层数据结构式链表数据结构(即后面一个元素记录前一个),

                            特点:查询速度慢,因为每个元素只知道前面一个元素,但增删速度快

                            因为元素再多,增删一个,只要让其前后的元素重新相连即可

                            线程是不同步的。                           

                |--->Vector(JDK1.0):底层数据结构是数组数据结构.特点是查询和增删速度都很慢。

                        默认长度是10,当超过长度时,按100%延长集合长度。

                        线程同步。

                        (Vector功能跟ArrayList功能一模一样,已被ArrayList替代)

 

  |--->Set:集合,元素是无序的(因为没有索引),元素不可以重复。可以有null元素。

           |--->HashSet(JDK1.2):底层数据结构是哈希表、存取速度快、元素唯一、线程不同步。保证性元素唯一的原理:

                     先判断元素的hashCode值是否相同,再判断两元素的equals方法是否为true(往HashSet里面存的自定义元素要复写hashCode和equals方法,

以保证元素的唯一性!)

            |--->TreeSet:底层数据结构式二叉树。可以对Set集合中的元素进行排序。元素有序、线程不同步。

 

            |--->ArrayList:

            (1)当往ArrayList里面存入元素没什么要求时,即只要求有序就行时;

            (2)当往ArrayList里面存入元素要求不重复时,比如存入学生对象,当同名同姓时视为同一个人,则不往里面存储。则定义学生对象时,需复写equals方法

               public boolean equals(Object obj)

               {

                if(!(objinstanceof Student))

                    returnfalse;

                Studentstu = (Student)obj;

                returnthis.name.equals(stu.name)&&this.age==stu.age;

               }

      则往ArrayList集合通过add存入学生对象时,集合底层自己会调用学生类的equals方法,判断重复学生则不存入。

      注:对于List集合,无论是add、contains、还是remove方法,判断元素是否相同,都是通过复写equals方法来判断!

 

|--->LinkedList

            (1)LinkLedist的特有方法:

                 boolean offerFirst(E e)  在此列表的开头插入指定的元素。

                 boolean offerLast(E e) 在此列表末尾插入指定的元素。

                 E peekFirst() 获取但不移除此列表的第一个元素;如果此列表为空,则返回 null。

                 E peekLast() 获取但不移除此列表的最后一个元素;如果此列表为空,则返回 null。

                 E pollFirst() 获取并移除此列表的第一个元素;如果此列表为空,则返回 null。

                 E pollLast() 获取并移除此列表的最后一个元素;如果此列表为空,则返回 null。

            (2)通过LinkLedist的特有方法,可以实现某些数据特殊方式的存取,比如堆栈和队列。保证元素唯一性的依据:compareTo方法return 0

 

Set集合使用注意事项:

(1)HashSet:

通过new的方式往HashSet里面存的元素的hashCode都不同,但通常我们定义对象, 比如学生对象时,虽然是new的两个学生对象,但是当他们name和age一样时,我们认为是同一个对象,所以为了保证元素的唯一性,我们通常在往HashSet集合里面存储元素时,在定义对象的类中通常复写hashCode和equals方法。

                  public int hashCode()

                  {

                returnname.hashCode()+age*39;

                  }

                  public boolean equals(Object obj)

                  {

                if(!(objinstanceof Student))

                    returnfalse;

                Studentstu = (Student)obj;

                returnthis.name.equals(stu.name)&&this.age==stu.age;

                  }


       HashSet是如何保证元素唯一性的呢?

            如果两元素的hashCode值不同,则不会调用equals方法

            如果两元素的hashCode值相同,则继续判断equals是否返回true;

            hashCode和equals方法虽然定义在自定义对象类里面,但不是我们手动调用而是往HashSet集合里面存储元素的时候,集合底层自己调用hashCode和equals它自己拿对象去判断,自己判断两元素是否是同一个元素。

(2)TreeSet:

TreeSet的第一种排序方式:

让元素自身具备比较性,元素需要实现comparable接口,覆盖compareTo方法,这种    方式也称为元素的自然顺序,或者叫做默认顺序。

TreeSet的第二种排序方式:【很重要的】

当元素自身不具备比较性时,或者具备的比较性不是所需要的。

这时就需要让集合自身具备比较性。<字符串本身具有比较性>

 

                 class StringLengthComparator implementsComparator

                 {

                    publicint compare(Object obj1,Object obj2)

                    {

                        Strings1 = (String)obj1;

                        Strings2 = (String)obj2;

                        intnum = new Integer(s1.length()).compareTo(new Integer(s2.length()));

                        if(num==0)

                            returns1.compareTo(s2);

                        returnnum;

                    }

                 }

                 class TreeSetTest

                 {

                    publicstatic void main(String[] args)

                    {

                        TreeSetts = new TreeSet(new StringLengthComparator());

                        ts.add("addfg");

                        ts.add("dfg");

                        ts.add("agtuug");

                        ts.add("vgjkg");

                        sop(ts);

                    }

                 }

 

                 

                                   

   基本数据类型或字符串对象均实现了Comparable接口,故同种类型基本数据间具备比较性,即自然顺序。

 

Map:顶层接口,该集合存储的是键值对,而且键是唯一的,Map和Set很像,Set集合底层就是使用了Map集合。

        Map集合没有迭代器,要取出元素必须先将Map集合转换成Set集合才能遍历元素

       |--->HashTable(JDK1.0):

        底层是哈希表数据结构;

        不可以使用null键和null值;

        用作键的对象必须实现hashCode和equals方法来保证键的唯一性

        线程同步,效率低

       |--->HashMap(JDK1.2):

        底层是哈希表数据结构;

        允许使用null键和null值;

        线程不同步,效率高;

        保证元素唯一性的:

        原理:先判断元素的hashCode值是否相同,再判断两元素的equals方法是否为true (往HashSet里面存的自定义元素要复写hashCode和equals方法,以保证元素的唯一性!)

        classStudent {

            privateString name;

            privateint age;

            publicStudent(String name, int age) {

                super();

                this.name= name;

                this.age= age;

            }

            publicint getAge() {

                returnage;

            }

            publicvoid setAge(int age) {

                this.age= age;

            }

            publicString getName() {

                returnname;

            }

            publicvoid setName(String name) {

                this.name= name;

            }

           

            @Override

            publicint hashCode(){

                returnname.hashCode()+age*34;

            }

            @Override

            publicboolean equals(Object obj){

               

                if(!(objinstanceof Student))

                    returnfalse;

                Studentstu = (Student)obj;

                returnthis.name.equals(stu.name)&&this.age==stu.age;

            }

        publicclass HashMapDemo1 {

            publicstatic void main(String[] args) {

                Map<Student, String> hmap = new HashMap<Student , String>();

                hmap.put(newStudent("001",20), "beijing");

                hmap.put(newStudent("002",25), "hebei");

                hmap.put(newStudent("003",50), "hainan");

                hmap.put(newStudent("001",20), "beijing");

               

                System.out.println(hmap.size());

                Set<Student>keySet = hmap.keySet();

                Iterator<Student>it = keySet.iterator();

                while(it.hasNext()){

                    Studentstu = it.next();

                    Stringaddr = hmap.get(stu);

                    System.out.println(stu.getName()+".."+stu.getAge()+"::"+addr);

                }  

            }  

              }   
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值