LinkedList适合频繁头尾插入删除,因双向链表结构使头尾操作时间复杂度为O(1),无需元素位移;但随机访问get(int index)较慢,为O(n),此时应选ArrayList。

因为LinkedList底层是双向链表,插入操作只需调整相邻节点的指针引用,无需移动其他元素,所以特别适合频繁在任意位置(尤其是头尾)插入或删除的场景。
插入操作时间复杂度是O(1)
在已知位置(比如头、尾,或已有节点引用)插入时,LinkedList不涉及元素位移——它只新建一个Node,修改前后两个节点的next和prev引用即可完成。例如:
-
addFirst():直接把新节点设为first,原首节点的prev指向它 -
addLast():类似地更新last和原尾节点的next -
add(int index, E e)虽需先遍历到位置(O(n)),但真正插入动作仍是O(1)
对比ArrayList:避免数组扩容和元素搬移
ArrayList底层是动态数组,插入可能触发以下开销:
- 尾部插入:多数情况快,但容量不足时要扩容(复制整个数组,O(n))
- 中间或头部插入:必须将插入点后所有元素整体后移(平均O(n))
- 内存连续性导致灵活性差:预分配空间易浪费,大对象频繁增删易引发GC压力
而LinkedList每个节点独立分配内存,用多少建多少,没有“批量搬移”问题。
立即学习“Java免费学习笔记(深入)”;
头尾操作有专属优化
LinkedList维护first和last两个瞬时引用,让头/尾操作完全避开遍历:
-
push()/pop()(栈)、offerFirst()/pollLast()(双端队列)全部是常数时间 - 实现请求队列、撤销栈、滑动窗口等结构时,天然契合高频头尾变更需求
注意适用边界
优势只在“改结构”场景成立;如果代码中大量使用get(int index)随机访问,LinkedList反而更慢(需从头或尾遍历,O(n)),此时应选ArrayList。
基本上就这些。











