Skip to content

Commit 1af0085

Browse files
author
gongtao02
committed
707.ts
1 parent 9576229 commit 1af0085

File tree

1 file changed

+198
-0
lines changed

1 file changed

+198
-0
lines changed

Diff for: 707.ts

+198
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,198 @@
1+
/*
2+
* @lc app=leetcode.cn id=707 lang=typescript
3+
*
4+
* [707] 设计链表
5+
*
6+
* https://leetcode.cn/problems/design-linked-list/description/
7+
*
8+
* algorithms
9+
* Medium (34.54%)
10+
* Likes: 1050
11+
* Dislikes: 0
12+
* Total Accepted: 335.4K
13+
* Total Submissions: 971K
14+
* Testcase Example: '["MyLinkedList","addAtHead","addAtTail","addAtIndex","get","deleteAtIndex","get"]\n' +
15+
'[[],[1],[3],[1,2],[1],[1],[1]]'
16+
*
17+
* 你可以选择使用单链表或者双链表,设计并实现自己的链表。
18+
*
19+
* 单链表中的节点应该具备两个属性:val 和 next 。val 是当前节点的值,next 是指向下一个节点的指针/引用。
20+
*
21+
* 如果是双向链表,则还需要属性 prev 以指示链表中的上一个节点。假设链表中的所有节点下标从 0 开始。
22+
*
23+
* 实现 MyLinkedList 类:
24+
*
25+
*
26+
* MyLinkedList() 初始化 MyLinkedList 对象。
27+
* int get(int index) 获取链表中下标为 index 的节点的值。如果下标无效,则返回 -1 。
28+
* void addAtHead(int val) 将一个值为 val
29+
* 的节点插入到链表中第一个元素之前。在插入完成后,新节点会成为链表的第一个节点。
30+
* void addAtTail(int val) 将一个值为 val 的节点追加到链表中作为链表的最后一个元素。
31+
* void addAtIndex(int index, int val) 将一个值为 val 的节点插入到链表中下标为 index 的节点之前。如果
32+
* index 等于链表的长度,那么该节点会被追加到链表的末尾。如果 index 比长度更大,该节点将 不会插入 到链表中。
33+
* void deleteAtIndex(int index) 如果下标有效,则删除链表中下标为 index 的节点。
34+
*
35+
*
36+
*
37+
*
38+
* 示例:
39+
*
40+
*
41+
* 输入
42+
* ["MyLinkedList", "addAtHead", "addAtTail", "addAtIndex", "get",
43+
* "deleteAtIndex", "get"]
44+
* [[], [1], [3], [1, 2], [1], [1], [1]]
45+
* 输出
46+
* [null, null, null, null, 2, null, 3]
47+
*
48+
* 解释
49+
* MyLinkedList myLinkedList = new MyLinkedList();
50+
* myLinkedList.addAtHead(1);
51+
* myLinkedList.addAtTail(3);
52+
* myLinkedList.addAtIndex(1, 2); // 链表变为 1->2->3
53+
* myLinkedList.get(1); // 返回 2
54+
* myLinkedList.deleteAtIndex(1); // 现在,链表变为 1->3
55+
* myLinkedList.get(1); // 返回 3
56+
*
57+
*
58+
*
59+
*
60+
* 提示:
61+
*
62+
*
63+
* 0 <= index, val <= 1000
64+
* 请不要使用内置的 LinkedList 库。
65+
* 调用 get、addAtHead、addAtTail、addAtIndex 和 deleteAtIndex 的次数不超过 2000 。
66+
*
67+
*
68+
*/
69+
70+
// @lc code=start
71+
class NodeItem {
72+
val: number = -1
73+
next: NodeItem | null = null
74+
pre: NodeItem | null = null
75+
constructor(val: number, next: NodeItem | null, pre: NodeItem | null,) {
76+
this.val = val
77+
this.next = next
78+
this.pre = pre
79+
}
80+
}
81+
class MyLinkedList {
82+
// 虚拟头节点
83+
head: NodeItem
84+
// 虚拟尾节点
85+
tail: NodeItem
86+
size = 0
87+
constructor() {
88+
this.head = new NodeItem(-1, null, null)
89+
this.tail = new NodeItem(-1, null, null)
90+
this.head.next = this.tail
91+
this.tail.pre = this.head
92+
this.size = 0
93+
}
94+
95+
get(index: number): number {
96+
if(!this.isElementIndex(index)) return -1
97+
//head, 0,1,2,3,4, tail
98+
let tmp = this.head
99+
for (let i = 0; i <= index; i++) {
100+
if (!tmp?.next) return -1
101+
tmp = tmp.next
102+
}
103+
return tmp.val
104+
}
105+
106+
travel() {
107+
let tmp = this.head.next
108+
const list: number[] = []
109+
while (tmp && tmp !== this.tail) {
110+
list.push(tmp.val)
111+
tmp = tmp.next
112+
}
113+
return list.join(',')
114+
}
115+
116+
addAtHead(val: number): void {
117+
// head , x, 0,1, tail
118+
const x = new NodeItem(val, this.head.next, this.head)
119+
this.head.next.pre = x
120+
this.head.next = x
121+
122+
this.size += 1
123+
124+
}
125+
126+
addAtTail(val: number): void {
127+
// val, x, tail
128+
const x = new NodeItem(val, this.tail, this.tail.pre)
129+
x.next.pre = x
130+
x.pre.next = x
131+
this.size += 1
132+
}
133+
134+
addAtIndex(index: number, val: number): void {
135+
if(!this.isPositionIndex(index)) return
136+
if (index < 0 || index > this.size) return
137+
// head, 0, 1,2,x,3 ,tail
138+
let pre = this.head
139+
for (let i = 0; i < index; i++) {
140+
if (!pre?.next) return
141+
pre = pre.next
142+
}
143+
// if(pre.next === this.tail)
144+
145+
let next = pre.next // next = 3
146+
const x = new NodeItem(val, next, pre)
147+
pre.next = x
148+
// TODO
149+
next!.pre = x
150+
this.size +=1
151+
}
152+
153+
deleteAtIndex(index: number): void {
154+
if(!this.isElementIndex(index)) return
155+
if (index < 0 || index > this.size) return
156+
// head, 0, 1,2,x,3 ,tail
157+
let pre = this.head
158+
for (let i = 0; i < index; i++) {
159+
if (!pre?.next) return
160+
pre = pre.next
161+
}
162+
let next = pre.next?.next
163+
164+
pre.next = next
165+
next.pre = pre
166+
this.size -=1
167+
}
168+
isElementIndex(index: number){
169+
return index >= 0 && index < this.size
170+
}
171+
isPositionIndex(index: number){
172+
return index >= 0 && index <= this.size
173+
}
174+
}
175+
176+
177+
/**
178+
* Your MyLinkedList object will be instantiated and called as such:
179+
* var obj = new MyLinkedList()
180+
* var param_1 = obj.get(index)
181+
* obj.addAtHead(val)
182+
* obj.addAtTail(val)
183+
* obj.addAtIndex(index,val)
184+
* obj.deleteAtIndex(index)
185+
*/
186+
// @lc code=end
187+
188+
const myLinkedList = new MyLinkedList();
189+
myLinkedList.addAtHead(1);
190+
console.log(myLinkedList.travel())
191+
myLinkedList.addAtTail(3);
192+
console.log(myLinkedList.travel())
193+
myLinkedList.addAtIndex(1, 2); // 链表变为 1->2->3
194+
console.log(myLinkedList.travel())
195+
console.log(myLinkedList.get(1))// 返回 2
196+
myLinkedList.deleteAtIndex(1); // 现在,链表变为 1->3
197+
console.log(myLinkedList.travel())
198+
console.log(myLinkedList.get(1)) // 返回 3

0 commit comments

Comments
 (0)