java 集合类

Collection


    Collection扩展了Iterable接口。数组和Iterable对象都可使用增强for循环遍历,但数组绝不是Iterable类型。在使用增强for循环时,会调用Iterable对象的iterator方法得到Iterator对象,然后再调用该Iterator对象的hasNext和next。Collection的iterator的remove方法要优于自带的remove方法,原因有两点:(1)Collection的remove必须首先找到要被删除的项,开销可能会比较大;(2)在使用Iterator或增强for循环时,同时对集合使用add、remove、clear等增删操作时会造成修改不同步的异常。

    在使用Iterator的remove方法时需注意一点:remove()移除的是由next()得到的元素,故在remove()之前先调用next()方法,否则会报IllegalStateException。

    Collection继承了Iterable对象而不是Iterator,与Iterator是依赖关系。从概念上讲,Collection是可迭代类型而不是迭代器类型。另外,让迭代逻辑与数据结构分离,好处是可在一种数据结构上实现多种迭代逻辑。

List

    List和Collection存在明显不同,尽管List所要求的方法都在Collection中。

    AbstractList中加入了ListIterator(为Iterator的子类型)。Iterator只能向前移动,而ListIterator可双向移动(next和previous)。还可以通过调用listIterator(n)创建一个一开始就指向列表索引为n的元素处的IistIterator。

(1)ArrayList

    一种可增长数组的实现,查询和修改很快,插入和删除代价昂贵(除非在末端进行)。在API中ArrayList的默认长度为10,超出时延长50%。改进:预先设置容量以避免容量的扩展,再使用trimToSize在所有添加操作完成后使用以避免浪费空间。

    ArrayList中indexOf查找元素时使用的是equals方法;contains使用了indexOf;containsAll使用了contains;remove使用了equals。

    注意:Arrays工具类中的asList方法返回的是Arrays.ArrayList类,并非java.util.ArrayList。Arrays.ArrayList继承自AbstractList,并未覆写其中的增删操作(使用add或delete等操作会报UnsupportedOperationException),为尺度固定的数组。

(2)LinkedList

    双链表实现,增删及访问表两端很快,但不容易索引,且get代价昂贵。改进:获取表中数据时可使用增强for循环。

    LinkedList特有方法:addFirst / addLast / getFirst / getLast / removeFirst / removeLast 

    JDK6后添加方法:    offerFirst / offerLast / peekFirst / peekLast / pollFirst / pollLast

    上述方法的区别在于:offXxx会返回boolean;peekXxx或pollXxx在集合为空时不会抛出异常而是返回null。

    另外返回boolean不代表是否添加成功,因为Collection规定一个集合拒绝添加一个元素时,不管什么原因,都必须抛出异常。返回boolean的意义在于操作完成后集合的内容是否改变了。

    LinkedList实现了Queue接口,添加了element(getFirst)/offer(add)/peek/poll/remove(removeFirst)方法。

(3)Vector

    数组结构,与ArrayList类似,但线程同步,增删查询都比ArrayList慢。API中默认长度为10,超出时延长100%。Vector还可以使用Enumeration类来获取元素,但由于枚举名称和方法名称过长,现已被Iterator替代。

(4)Stack

    栈是一个表,任何实现表的方法都能实现栈。流行的实现方法有2种:单链表和数组。更推荐使用数组。另外在压栈和出栈时速度非常快,因为现代计算机中,(整数的)push和pop都可对应成一条机器指令。

    栈的典型应用:平衡符合、后缀表达式、中缀到后缀的转换、方法调用(使用栈存放递归调用时需要保存的重要的值)。

    Stack继承自Vector,也是线程同步。

    peek:返回栈顶元素,但栈为空时会抛EmptyStackException;pop:移除并返回栈顶元素;push:将元素放入栈顶并返回该元素。

(5)Queue

    队列是典型的FIFO容器,即从容器的一端放入元素,从另一端取出元素,且放入顺序与取出顺序相同。

    在创建具有Queue功能的实现时,不需要使用Collection方法。

    队列的实现可以使用数组或链表。 对于数组实现队列,需要使用循环数组,但实现回绕可能会时运行时间加倍。 而在保证enqueue的次数不会大于队列容量的应用中,使用回绕是没有必要的。

    peek和element都将返回队头。队列为空时,peek返回null,而element会抛NoSuchElementException;poll和remove都将移除并返回队头。队列为空时,poll返回null,而remove会抛NoSuchElementException。

    PriorityQueue是一种优先级队列(通常会维护一个堆),即容器中下一个弹出的元素是最需要的(优先级最高的)元素。默认排序为对象在队列中的自然顺序,可通过Comparator修改优先级。

Set

    Set具有与Collection完全一样的接口,实际上Set就是Collection,只是行为不同。 除TreeSet外所有Set都拥有与Collection完全一样的接口。

(1)HashSet

    HashSet使用的是散列函数,内部数据结构是HashMap。判断元素是否重复,会先比较hashcode,若相同再使用equals比较。故为提高效率,在存元素时尽量保证hash值唯一。

(2)TreeSet

    TreeSet将元素存储在红—黑树数据结构中,默认使用ACSII值排序。

    存入TreeSet的元素要具备比较性,即要实现Comparable接口,调用compareTo方法,比较对象内容,也称自然排序。另外,当元素自身不具备比较性时,需要在TreeSet构造函数中加入比较器(实现Comparator)。元素排序时以比较器为主。

Map


     Map与Collection间的唯一重叠就是Map可使用keySet、entrySet和vaules方法产生Collection。Map的keySet返回键的Set;values返回值得Collection;entrySet返回键值对Entry<K,V>的Set。

(1)HashTable

    Hashtable是基于陈旧的Dictionary类的,HashMap是Java 1.2引进的Map接口的一个实现。

    1、HashTable是线程同步的;

    2、HashTable不允许null值(key和value都不可以),HashMap允许null值(key和value都可以,只容许有一个null值的key,可以有多个null值的value);

    3、HashTable使用Enumeration,HashMap使用Iterator;

    4、HashTable中hash数组默认大小是11,增加的方式是 old*2+1。HashMap中hash数组的默认大小是16,而且一定是2的指数;

    5、哈希值的使用不同。

HashTable直接使用对象的hashCode:

    int hash = key.hashCode();

    int index = (hash & 0x7FFFFFFF) % tab.length;

而HashMap重新计算hash值,而且用与代替求模:

    int hash = hash(k);

    int i = indexFor(hash,table.length);

static int hash(Object x) {
   int h = x.hashCode();
   h += ~(h << 9);
   h ^= (h >>> 14);
   h += (h << 4);
   h ^= (h >>> 10);
   return h;
}
static int indexFor(int h, int length) {
   return h & (length-1);
}

(2)HashMap

(3)TreeMap

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值