LinkedList源码小记

  1. LinkedList#clear()方法并不是简单的将lastfirst节点置为null,而是遍历所有节点,分别将每个节点置为null也就说LinkedList#clear()时间复杂度不是O(1)而是O(n)
       public void clear() {
           // Clearing all of the links between nodes is "unnecessary", but:
           // - helps a generational GC if the discarded nodes inhabit
           //   more than one generation
           // - is sure to free memory even if there is a reachable Iterator
           for (Node<E> x = first; x != null; ) {
               Node<E> next = x.next;
               x.item = null;
               x.next = null;
               x.prev = null;
               x = next;
           }
           first = last = null;
           size = 0;
           modCount++;
       }
    

    可以看到相关解释:

    1. 在分代GC中,通常List本身和较旧的节点一般处于比其他节点更老的一代,这样就好导致在发现所有节点都是垃圾之前,年轻的节点并没有被回收而且已经被复制了好几次,这几次复制都是无用功。
    2. 在调用这个方法后,即使迭代器还持有它们的引用,这些节点也会被回收。
  2. LinkedList实现了Deque接口,Deque中,包含了容器,栈,队列。因此在需要栈,队列的时候,可以使用Deque接口

poll,peek

由于LinkedList实现的特殊性。LinkedList提供了无参remove()方法来默认删除第一个元素。但是有些时候列表中没有任何元素,而对于队列,堆栈等一般都使用循环获取元素,这个时候LinkedList提供了两种方式来判断循环是否到了队尾或队头:

remove()/removeFirst()/removeLast()/element/getFirst()/ getLast() : 当容器为空的时候,抛出异常

poll()/pollFirst()/pollLast()/peek()/peekFirst()/peekLast(): 当容器为空的时候,返回null

add()/addFirst()/addLast() :当添加失败的时候,抛出异常(某些时候有些容器可能有大小限制)

offer()/offerFirst()/offerLast():当添加失败的时候,返回false

更多的区分

根据JDK的描述,

LinkedList各个方法中:

pop() //相当于remove()

push() //相当于 addFirst()

用于Stack


peek()/element()

poll()/remove()

offer()/add()

用于Queue

总结:

remove系列对应poll

get系列对应peek

add系列对应offer

其中:

栈是先进后出,专用对应方法为push(addFirst),pop(remove)

队列是先进先出,专用对应方法为offer(),poll()