篇章六 数据结构——链表(二)

目录

[1. LinkedList的模拟实现](#1. LinkedList的模拟实现)

[1.1 双向链表结构图​编辑](#1.1 双向链表结构图编辑)

[1.2 三个简单方法的实现](#1.2 三个简单方法的实现)

[1.3 头插法](#1.3 头插法)

[1.4 尾插法](#1.4 尾插法)

[1.5 中间插入](#1.5 中间插入)

[1.6 删除 key](#1.6 删除 key)

[1.7 删除所有key](#1.7 删除所有key)

[1.8 clear](#1.8 clear)

2.LinkedList的使用

[2.1 什么是LinkedList](#2.1 什么是LinkedList)

[5.2 LinkedList的使用](#5.2 LinkedList的使用)

1.LinkedList的构造

[2. LinkedList的其他常用方法介绍](#2. LinkedList的其他常用方法介绍)

3.LinkedList的遍历33.

[5.3 ArrayList 和 LinkedList的区别](#5.3 ArrayList 和 LinkedList的区别)


1. LinkedList的模拟实现

1.1 双向链表结构图

1.2 三个简单方法的实现

java 复制代码
@Override
    public void display() {
        ListNode cur = head;
        while (cur != null) {
            System.out.print(cur.val + " ");
            cur = cur.next;
        }
        System.out.println();
    }

    @Override
    public int size() {
        int len = 0;
        ListNode cur = head;
        while (cur != null) {
            len++;
            cur = cur.next;
        }
        return len;
    }

    @Override
    public boolean contains(int key) {
        ListNode cur = head;
        while (cur != null) {
            if (cur.val == key) {
                return true;
            }
            cur = cur.next;
        }
        return false;
    }

此处和单链表一样,不在赘述。

1.3 头插法

java 复制代码
    @Override
    public void addFirst(int data) {
        ListNode node = new ListNode(data);
        if (head == null) {
            head = last = node;
        }else {
            node.next = head;
            head.prev = node;
            head = node;
        }
    }

1.4 尾插法

java 复制代码
    @Override
    public void addLast(int data) {
        ListNode node = new ListNode(data);
        if (head == null) {
            last = head = node;
        }else {
            last.next = node;
            node.prev = last;
            last = last.next;
        }
    }

1.5 中间插入

java 复制代码
@Override
public void addIndex(int index, int data) {
    int len = size();
    if (index < 0 || index > len) {
        return;
    }

    if (index == 0) {
        addFirst(data);
        return;
    }

    if (index == len) {
        addLast(data);
        return;
    }

    // 中间插入
    ListNode node = new ListNode(data);
    ListNode cur = findIndex(index);
    node.next = cur;
    cur.prev.next = node;
    node.prev = cur.prev;
    cur.prev = node;
}
private ListNode findIndex(int index) {
    ListNode cur = head;
    while (index != 0) {
        cur = cur.next;
        index--;
    }
    return cur;
}

此处直接找到 index 位置即可,不需要找 index - 1,因为有 prev

1.6 删除 key

java 复制代码
@Override
    public void remove(int key) {
        ListNode cur = head;
        while (cur != null) {
            if (cur.val == key) {
                // 开始删除
                if (cur == head) {
                    head = head.next;
                    if (head != null) {
                        head.prev = null;
                    }
                } else {
                    cur.prev.next = cur.next;
                    if (cur.next == null) {
                        last = last.prev;
                    }else {
                        cur.next.prev = cur.prev;
                    }
                }
                return;
            }
            cur = cur.next;
        }
    }

注意:

1.此处最关键的代码:

cur.prev.next = cur.next;

cur.next.prev = cur.prev;

2.但是很显然解决不了头节点和尾节点,需要条件语句单独处理

3.特殊情况:

只有一个节点的链表,且为key值

需要加上判断逻辑:

if (head != null) {

head.prev = null;

}

1.7 删除所有key

java 复制代码
@Override
    public void removeAllKey(int key) {
        ListNode cur = head;
        while (cur != null) {
            if (cur.val == key) {
                // 开始删除
                if (cur == head) {
                    head = head.next;
                    if (head != null) {
                        head.prev = null;
                    }
                } else {
                    cur.prev.next = cur.next;
                    if (cur.next == null) {
                        last = last.prev;
                    }else {
                        cur.next.prev = cur.prev;
                    }
                }
            }
            cur = cur.next;
        }
    }

注意:

很显然将 删除key代码中的 return;删除即可

1.8 clear

java 复制代码
    @Override
    public void clear() {
        ListNode cur = head;

        while (cur != null) {
            ListNode curNext = cur.next;
            cur.prev = null;
            cur.next = null;
            cur = curNext;
        }
        head = null;
        last = null;
    }

2.LinkedList的使用

2.1 什么是LinkedList

LinkedList 的官方文档

LinkedList的底层是双向链表结构 ,由于链表没有将元素存储在连续的空间中,元素存储在单独的节点中,然后通过引用将节点连接起来了,因此在在任意位置插入或者删除元素 时,不需要搬移元素,效率比较高

在集合框架中,LinkedList也实现了List接口,具体如下:

【说明】

  1. LinkedList实现了List接口

  2. LinkedList的底层使用了双向链表

  3. LinkedList没有实现RandomAccess接口,因此LinkedList不支持随机访问

  4. LinkedList的任意位置插入和删除元素时效率比较高,时间复杂度为O(1)

  5. LinkedList比较适合任意位置插入的场景

5.2 LinkedList的使用

1.LinkedList的构造

2. LinkedList的其他常用方法介绍

3.LinkedList的遍历33.

java 复制代码
 public static void main(String[] args) {
        LinkedList<Integer> linkedList2 = new LinkedList<>();

        linkedList2.add(1);
        linkedList2.addLast(3);
        linkedList2.addLast(4);
        linkedList2.addLast(5);
        System.out.println(linkedList2);

        System.out.println("=========ListIterator=========");
        ListIterator<Integer> listIterator = linkedList2.listIterator(linkedList2.size());
        while (listIterator.hasPrevious()) {
            System.out.print(listIterator.previous() + " ");
        }
        System.out.println();

        System.out.println("=========ListIterator=========");
        ListIterator<Integer> listIterator1 = linkedList2.listIterator();
        while (listIterator1.hasNext()) {
            System.out.print(listIterator1.next() + " ");
        }
        System.out.println();

        System.out.println("=========Iterator=========");
        Iterator<Integer> iterator = linkedList2.iterator();
        while (iterator.hasNext()) {
            System.out.print(iterator.next() + " ");
        }
        System.out.println();

        System.out.println("=========for each=========");
        for (Integer x : linkedList2) {
            System.out.print(x + " ");
        }
        System.out.println();

        System.out.println("=========for=========");
        for (int i = 0; i < linkedList2.size(); i++) {
            System.out.print(linkedList2.get(i) + " ");
        }
        System.out.println();


    }

5.3 ArrayList 和 LinkedList的区别

相关推荐
随缘而动,随遇而安2 小时前
第八十八篇 大数据中的递归算法:从俄罗斯套娃到分布式计算的奇妙之旅
大数据·数据结构·算法
水木兰亭5 小时前
数据结构之——树及树的存储
数据结构·c++·学习·算法
Jess076 小时前
插入排序的简单介绍
数据结构·算法·排序算法
老一岁6 小时前
选择排序算法详解
数据结构·算法·排序算法
freexyn7 小时前
Matlab自学笔记六十一:快速上手解方程
数据结构·笔记·matlab
ysa0510307 小时前
Dijkstra 算法#图论
数据结构·算法·图论
醇醛酸醚酮酯9 小时前
基于多线程实现链表快排
数据结构·链表
小张成长计划..10 小时前
数据结构-栈的实现
开发语言·数据结构
一只鱼^_12 小时前
基础算法合集-图论
数据结构·算法·深度优先·图论·广度优先·宽度优先·图搜索算法
小张成长计划..13 小时前
双向链表的实现
数据结构·链表