s0142
This commit is contained in:
70
src/s0142_linked_list_cycle.cpp
Normal file
70
src/s0142_linked_list_cycle.cpp
Normal file
@@ -0,0 +1,70 @@
|
||||
#include "s0142_linked_list_cycle.hpp"
|
||||
|
||||
IterResult S0142::iter(ListNode *fast, ListNode *slow, bool startUp) {
|
||||
// 终止条件
|
||||
if (fast == nullptr || slow == nullptr) {
|
||||
return {nullptr, false};
|
||||
}
|
||||
if (fast->next == nullptr) {
|
||||
return {nullptr, false};
|
||||
}
|
||||
if (slow->next == slow) {
|
||||
return {slow, true};
|
||||
}
|
||||
// 当两指针相遇时同样达到终止条件
|
||||
if (fast == slow && !startUp) {
|
||||
return {nullptr, true};
|
||||
}
|
||||
// 递归
|
||||
IterResult result = iter(fast->next->next, slow->next, false);
|
||||
// 从后往前遍历
|
||||
// 达到了终止条件,但是没有两个指针遇见过
|
||||
// 这说明没有环
|
||||
if (!result.meet) {
|
||||
return {nullptr, false};
|
||||
} else {
|
||||
// 有环的情况
|
||||
// 我们把 fast 和 fast-next 节点所经过的足迹全部记录下来
|
||||
// key 是所经过的节点
|
||||
// value 是所经过的次数
|
||||
if (footprint.count(fast) == 0) {
|
||||
footprint[fast] = 1;
|
||||
} else {
|
||||
footprint[fast] += 1;
|
||||
}
|
||||
if (footprint.count(fast->next) == 0) {
|
||||
footprint[fast->next] = 1;
|
||||
} else {
|
||||
footprint[fast->next] += 1;
|
||||
}
|
||||
// 什么情况下是环的入口呢?
|
||||
// 1. footprint[fast] == 1 && footprint[fast->next] > 1
|
||||
// 2. footprint[fast->next] == 1 && footprint[fast->next->next] > 1
|
||||
if (footprint.count(fast) == 1 && footprint.count(fast->next) == 1) {
|
||||
if (footprint[fast] == 1 && footprint[fast->next] > 1) {
|
||||
return {fast->next, true};
|
||||
}
|
||||
}
|
||||
if (footprint.count(fast->next) == 1 &&
|
||||
footprint.count(fast->next->next) == 1) {
|
||||
if (footprint[fast->next] == 1 && footprint[fast->next->next] > 1) {
|
||||
return {fast->next->next, true};
|
||||
}
|
||||
}
|
||||
// 返回
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
ListNode *S0142::detectCycle(ListNode *head) {
|
||||
if (head == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
if (head->next == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
// 递归函数无法处理所有节点都在环里的情况,所以在这里加一个哑节点
|
||||
ListNode dummy = ListNode(0);
|
||||
dummy.next = head;
|
||||
return iter(&dummy, &dummy, true).node;
|
||||
}
|
Reference in New Issue
Block a user