# 设计链表
前言:4 号 提交了 5 次全部失败 这里贴一下失败的尝试,设计链表非常考研程序整体的结构 一个方法出现纰漏 ,后面会出现各种问题。
# 题目
你可以选择使用单链表或者双链表,设计并实现自己的链表。
单链表中的节点应该具备两个属性:
val和next。val是当前节点的值,next是指向下一个节点的指针 / 引用。如果是双向链表,则还需要属性
prev以指示链表中的上一个节点。假设链表中的所有节点下标从 0 开始。实现
MyLinkedList类:
MyLinkedList()初始化MyLinkedList对象。int get(int index)获取链表中下标为index的节点的值。如果下标无效,则返回-1。void addAtHead(int val)将一个值为val的节点插入到链表中第一个元素之前。在插入完成后,新节点会成为链表的第一个节点。void addAtTail(int val)将一个值为val的节点追加到链表中作为链表的最后一个元素。void addAtIndex(int index, int val)将一个值为val的节点插入到链表中下标为index的节点之前。如果index等于链表的长度,那么该节点会被追加到链表的末尾。如果index比长度更大,该节点将 不会插入 到链表中。void deleteAtIndex(int index)如果下标有效,则删除链表中下标为index的节点。示例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14 输入
["MyLinkedList", "addAtHead", "addAtTail", "addAtIndex", "get", "deleteAtIndex", "get"]
[[], [1], [3], [1, 2], [1], [1], [1]]
输出
[null, null, null, null, 2, null, 3]
解释
MyLinkedList myLinkedList = new MyLinkedList();
myLinkedList.addAtHead(1);
myLinkedList.addAtTail(3);
myLinkedList.addAtIndex(1, 2); // 链表变为 1->2->3
myLinkedList.get(1); // 返回 2
myLinkedList.deleteAtIndex(1); // 现在,链表变为 1->3
myLinkedList.get(1); // 返回 3提示:
0 <= index, val <= 1000- 请不要使用内置的 LinkedList 库。
- 调用
get、addAtHead、addAtTail、addAtIndex和deleteAtIndex的次数不超过2000。
# 失败代码
1 | public class MyLinkedNode |
好 那写之前我决定看视频先学习一下
-
获取第 n 个节点的值
- 合法性判断 : n<0 且 n> size-1 都是不合法的
- 定义临时指针 cur 为 dummyHead -> next;
- 记住极端情况 获取第 0 个的情况
-
头部插入节点
- new 一个新 Node
- new.next = dummy .next (注意这里的顺序 如果和 3 反了 会导致连接错误)
- dummy.next = new
- size++
-
尾部插入节点
- cur = dummy
- while (cur.next != null) 为空为终止条件
- cur.next = newNode
-
第 n 个节点前插入节点
- cur = dummy
- while (n–){ cur = cur.next} n 为 0 的时候 终止
- 和插入一样 如下图顺序
-
image-20240407212448058
-
删除第 n 个节点
- cur= dummy
- 第 n 个节点一定要是 cur.next 然后我们操作第 cur 个节点
- 一样 while (n–) cur= cur.next 第 n 个为 cur.next
- cur.next = cur.next.next; 指向下下个 为 null 也不要紧 n 记得前面要防止极端条件
- size–
好了 船新代码:
1 | public class MyLinkedNode |
要注意几个点 一个是 插入的时候 按照需求 index<0 并不是不合法 而是 直接插入头结点 。