Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 0df19f6

Browse files
author
ggl
committed
优化链表快慢指针相关代码
1 parent e516247 commit 0df19f6

File tree

4 files changed

+60
-43
lines changed

4 files changed

+60
-43
lines changed

Algorithm/LinkedList/main.swift

Lines changed: 24 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -11,21 +11,24 @@ import Foundation
1111
//MARK: - 单链表
1212
let singlyLinkedList = SinglyLinkedList()
1313
singlyLinkedList.print()
14+
print("===============创建链表====================")
1415
for i in 1...10 {
1516
singlyLinkedList.addNode(i)
1617
}
1718
singlyLinkedList.print()
1819

20+
print("===============删除链表结点(7,1,2,10)============")
1921
singlyLinkedList.deleteNode(7)
2022
singlyLinkedList.deleteNode(1)
2123
singlyLinkedList.deleteNode(2)
2224
singlyLinkedList.deleteNode(10)
2325
singlyLinkedList.print()
26+
print("===============添加链表结点(12)============")
2427
singlyLinkedList.addNode(12)
2528
singlyLinkedList.print()
26-
print("=================================================\n")
2729

2830
//MARK: - 循环链表
31+
print("===============循环链表操作================")
2932
let loopLinkedList = LoopLinkedList()
3033
loopLinkedList.print()
3134

@@ -37,10 +40,10 @@ loopLinkedList.deleteNode(2)
3740
loopLinkedList.deleteNode(10)
3841
loopLinkedList.print()
3942
let tailNode = loopLinkedList.tailNode()!
40-
print("头结点值: \(loopLinkedList.head!.data), 尾结点的下一个结点值: \(tailNode.next!.data)")
41-
print("=================================================\n")
43+
print("循环链表头结点值: \(loopLinkedList.head!.data), 尾结点的下一个结点值: \(tailNode.next!.data)")
4244

4345
//MARK: - 双向链表
46+
print("==============双向链表操作=================")
4447
let doublyLinkedList = DoublyLinkedList()
4548
doublyLinkedList.print()
4649

@@ -59,6 +62,9 @@ print("=================================================\n")
5962
print("单链表反转")
6063
singlyLinkedList.reverse()
6164
singlyLinkedList.print()
65+
print("递归反转")
66+
singlyLinkedList.head = singlyLinkedList.reverse(singlyLinkedList.head)
67+
singlyLinkedList.print()
6268

6369
print("\n合并两个有序单链表为一个有序单链表")
6470
let linkedListOne = SinglyLinkedList()
@@ -76,8 +82,16 @@ linkedListTwo.addNode(7)
7682
linkedListTwo.addNode(14)
7783
linkedListTwo.print()
7884

79-
let mergeList = mergeLinkedList(linkedListOne: linkedListOne, linkedListTwo: linkedListTwo)
80-
mergeList.print()
85+
let mergeNode = mergeLinkedList(linkedListOne: linkedListOne.head, linkedListTwo: linkedListTwo.head)
86+
if let node = mergeNode {
87+
print("\(node.data)", terminator: "")
88+
}
89+
var nextNode = mergeNode?.next
90+
while nextNode != nil {
91+
print(" -> \(nextNode!.data)", terminator: "")
92+
nextNode = nextNode?.next
93+
}
94+
print("")
8195

8296
print("=================================================")
8397
print("求链表的中间结点")
@@ -92,10 +106,12 @@ if let middleNode = linkedList.middleNode() {
92106

93107
print("=================================================")
94108
linkedList.print()
95-
let lastK = 2
96-
print("求链表的倒数第\(lastK)个结点")
109+
let lastK = Int.random(in: 0...10)
110+
print("求链表的倒数第\(lastK)个结点: ", terminator: "")
97111
if let lastKNode = linkedList.lastKNode(lastK: lastK) {
98-
print(lastKNode.data)
112+
print("结点值为: \(lastKNode.data)")
113+
} else {
114+
print("结点不存在")
99115
}
100116

101117
print("=================================================")

BinaryTree/BinaryTree.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -239,7 +239,7 @@ extension BinaryTree {
239239
}
240240
let leftH = treeHeight(node: node?.left)
241241
let rightH = treeHeight(node: node?.right)
242-
return max(leftH, rightH) + 1
242+
return Swift.max(leftH, rightH) + 1
243243
}
244244
}
245245

LinkedList/LinkedListFunc.swift

Lines changed: 13 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,9 @@ import Foundation
1414
/// - linkedListOne: 第一个有序单链表
1515
/// - linkedListTwo: 第二个有序单链表
1616
/// - Returns: 合并有序的单链表
17-
func mergeLinkedList(linkedListOne: SinglyLinkedList, linkedListTwo: SinglyLinkedList) -> SinglyLinkedList {
17+
func mergeLinkedList(linkedListOne: Node?, linkedListTwo: Node?) -> Node? {
1818
// 判断链表是否为空
19-
var p = linkedListOne.head, q = linkedListTwo.head
19+
var p = linkedListOne, q = linkedListTwo
2020
if p == nil {
2121
return linkedListTwo
2222
}
@@ -25,25 +25,21 @@ func mergeLinkedList(linkedListOne: SinglyLinkedList, linkedListTwo: SinglyLinke
2525
return linkedListOne
2626
}
2727

28-
let mergeLinkedList = SinglyLinkedList()
29-
while p != nil || q != nil {
30-
if p == nil {
31-
mergeLinkedList.addNode(q!.data)
32-
q = q?.next
33-
} else if q == nil {
34-
mergeLinkedList.addNode(p!.data)
28+
// 开始合并链表
29+
let newHead = Node(data: 0, next: nil)
30+
var temp: Node? = newHead
31+
while p != nil && q != nil {
32+
if p!.data <= q!.data {
33+
temp?.next = p
3534
p = p?.next
3635
} else {
37-
if p!.data > q!.data {
38-
mergeLinkedList.addNode(q!.data)
39-
q = q?.next
40-
} else {
41-
mergeLinkedList.addNode(p!.data)
42-
p = p?.next
43-
}
36+
temp?.next = q
37+
q = q?.next
4438
}
39+
temp = temp?.next
4540
}
46-
return mergeLinkedList
41+
temp?.next = (p == nil ? q : p)
42+
return newHead.next
4743
}
4844

4945
/// 判断链表是否有环

LinkedList/SinglyLinkedList.swift

Lines changed: 22 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -89,26 +89,30 @@ class SinglyLinkedList {
8989
return
9090
}
9191

92-
var p = head
93-
var q = head?.next
92+
// pre指针指向前一个结点、cur指针指向当前需要反转的结点
93+
var pre = head
94+
var cur = head?.next
9495
head?.next = nil
95-
while q != nil {
96-
let w = q?.next
97-
q?.next = p
98-
p = q
99-
q = w
96+
while cur != nil {
97+
let next = cur?.next
98+
cur?.next = pre
99+
100+
// 进行下次循环
101+
pre = cur
102+
cur = next
100103
}
101-
head = p
104+
head = pre
102105
}
103106

104107
/// 递归反转
108+
@discardableResult
105109
func reverse(_ node: Node?) -> Node? {
106110
if node == nil || node?.next == nil {
107111
return node
108112
}
109113
// 注意,始终返回尾结点
110114
let newHead = reverse(node?.next)
111-
// 防止形成环
115+
// 防止形成环,例如1 -> 2 -> 3 <- 4 <- 5,当前 node 为 2,需要反转链表
112116
node?.next?.next = node
113117
node?.next = nil
114118
return newHead
@@ -123,10 +127,10 @@ class SinglyLinkedList {
123127
}
124128

125129
var slow = head
126-
var cur = head?.next
127-
while cur != nil {
130+
var fast = head
131+
while fast?.next != nil && fast?.next?.next != nil {
128132
slow = slow?.next
129-
cur = cur?.next?.next
133+
fast = fast?.next?.next
130134
}
131135
return slow
132136
}
@@ -140,18 +144,19 @@ class SinglyLinkedList {
140144
return nil
141145
}
142146

143-
if lastK == 1 {
144-
let tailNode = self.tailNode()
145-
return tailNode
146-
}
147-
147+
// 使用快、慢指针来解决
148148
var slow = head
149149
var fast = head
150150
// 快指针先走K步
151151
for _ in 0..<lastK-1 {
152152
fast = fast?.next
153153
}
154154

155+
// 如果快指针走出去了,则表示K值过大,返回nil
156+
if fast == nil {
157+
return nil
158+
}
159+
155160
// 快慢指针一起走,快指针走到头后慢指针位置则为倒数第K个结点
156161
while fast?.next != nil {
157162
slow = slow?.next

0 commit comments

Comments
 (0)