再探Java集合系列—LinkedList

单向链表

双向链表

LinkedList适用于什么场景?

适用于需要频繁插入和删除元素的场景,例如消息聊天系统,一开始并不明确有多少记录,可以在空间满足的情况下不断增加数据

LinkedList的特点有哪些?

  • LinkedList的底层采用了双向链表数据结构(好处是随即增删改元素快速,不涉及到元素位移)
  • 检索效率低(每次需要节点开始逐个往下进行检索,直到找到位置)
  • 在空间存储上内存地址不连续

链表的优缺点有哪些?

链表的优点:

**增删效率比较高。**由于链表上的元素在空间存储上内存地址不连续,所以随即增删元素的时候不会有大量元素位移,只需要修改元素指针域指向的位置就行

链表的缺点:

**检索效率低。**不能通过数学表达式计算被查找元素的内存地址,所以每次查找的时候都是从头节点开始遍历,直到找到位置

底层原理

测试用例:

复制代码
package List;
import java.util.LinkedList;

public class LinkedListTest {
    public static void main(String[] args) {
        LinkedList<String> list = new LinkedList<>();

        //添加元素
        list.add("张三1");
        list.add("张三2");
        list.add("张三3");
        list.add("张三4");
        list.add("张三5");

        //删除元素
        list.remove();      //删除第一个节点
        list.remove("张三2");  //删除指定元素的节点
        list.remove(3);  //删除指定位置的节点
        list.removeFirst();    //删除第一个节点
        list.removeLast();   //删除最后一个节点

        //更新元素
        list.set(2, "下标为3的元素更新");

        //查找元素
        list.indexOf("下标为3的元素更新");    //查找某个元素的位置
        list.get(3);   //查找指定位置的元素
    }
}
添加元素------add

在LinkedList的底层维护了一个内部类Node,链表中的每一个节点就是一个一个的Node节点组成

获取last节点、创建新节点

  • 判断last节点是否为空,为空说明此时并没有节点,也就不存在first和last指向任何一个节点
  • 如果last节点不为空,将新节点链接到链表的尾部
删除元素------remove

①、删除第一个元素------remove()

当使用remove方法不传任何参数的时候默认是删除链表的第一个元素,需要修改的内容:

如果是空链表,直接报异常

如果不是空链表:

  • 获取要删除节点的下一个节点
  • 使first指向要删除节点的下一个节点
  • 将要删除节点的下一个节点的prev为null(前面没有任何节点需要指向)
  • 对删除节点的item、next、prev置空

②、删除指定元素的节点------remove(Object o)

按照元素内容删除,这一步涉及到遍历链表,需要去查找要删除元素所在的节点,查找之后会调用专门用于删除节点的unlink方法

③、删除指定位置的节点------remove(int index)

unlink和上述相同,不做解释

④、删除第一个节点------removeFirst

⑥、删除最后一个节点------removeLast

从上面的例子结果发现:如果删除第一第一个和最后一个节点都不需要遍历

删除第一个节点:修改first指向为第二个节点,第二个节点的前驱指针为null

删除最后一个节点:修改last指向为倒数第二个节点

更新元素------set

在执行Node<E> node(int index) 方法的时候内部会对链表长度右移一位,这是为什么?

其实是一种分治的思想,右移一位相当于链表的长度除以2,根据传入的索引号确定要更新的元素是在链表的前半部分还是后半部分,如果是在链表的前半部分则链表的后半部分不需要在进行遍历,只需要遍历前半部分就可以,能够大大提高效率。

所以我们可以发现当我们要遍历的元素月靠近链表的中间位置,遍历所需要花费的时间越长

查找元素------indexOf、get

在实际场景中如何选择是使用LinkedList还是ArrayList?

  • 如果涉及到随机增删元素的业务比较多时,使用LinkedList
  • 如果涉及到检索,使用ArrayList

注:不同的数据结构在某些方面发挥的效果不一样

如果有想要交流的内容欢迎在评论区进行留言,如果这篇文档受到了您的喜欢那就留下你点赞+收藏+评论脚印支持一下博主~

相关推荐
@ chen26 分钟前
Spring Boot 解决跨域问题
java·spring boot·后端
洛_尘1 小时前
Java EE进阶2:前端 HTML+CSS+JavaScript
java·前端·java-ee
转转技术团队2 小时前
转转上门隐私号系统的演进
java·后端
皮皮林5512 小时前
Java+Selenium+快代理实现高效爬虫
java
hqxstudying3 小时前
Java行为型模式---策略模式
java·开发语言·建造者模式·适配器模式·策略模式
lxsy3 小时前
spring-ai-alibaba 简化版NL2SQL
java·nl2sql·spring-ai·ai-alibaba
WanderInk3 小时前
依赖对齐不再“失联”:破解 feign/BaseBuilder 错误实战
java·后端·架构
菜鸡上道3 小时前
Maven入门指南:生命周期、阶段和执行顺序详解
java·maven
许苑向上3 小时前
分布式缓存击穿以及本地击穿解决方案
java·分布式·缓存
爱Java&Java爱我3 小时前
数组:从键盘上输入10个数,合法值为1、2或3,不是这三个数则为非法数字,试编辑统计每个整数和非法数字的个数
java·开发语言·算法