목록을 감안할 때, 체인 링의 시작으로 첫 번째 노드를 반환합니다. 체인 비순환 경우가 반환됩니다 null
.
목록 주어진 반지를 보여주기 위해, 우리는 정수를 사용 pos
(인덱스 0부터 시작)리스트의리스트의 마지막에 연결된 위치를 나타냅니다. 경우 pos
이며 -1
,이 목록에는 루프가 없습니다.
설명 : 주어진 목록을 수정할 수 없습니다.
링크 된 목록을 감안할 때,주기가 시작되는 노드를 반환합니다. 어떤주기가없는 경우, 반환 null
.
주어진 연결리스트의주기를 표현하기 위해, 우리는 정수 사용 pos
꼬리에 연결하는 연결리스트에서 (0 인덱스) 위치를 나타냅니다. 경우 pos
이며 -1
, 다음 링크 된 목록에주기가 없다.
참고 : 링크 된 목록을 수정하지 마십시오.
예 1 :
输入:head = [3,2,0,-4], pos = 1
输出:tail connects to node index 1
解释:链表中有一个环,其尾部连接到第二个节点。
예 2 :
输入:head = [1,2], pos = 0
输出:tail connects to node index 0
解释:链表中有一个环,其尾部连接到第一个节点。
예 3 :
输入:head = [1], pos = -1
输出:no cycle
解释:链表中没有环。
고급 : 이 문제를 해결할 수있는 여분의 공간이 필요하십니까?
- 후속 : 당신은 여분의 공간을 사용하지 않고 해결할 수 있습니까?
문제 해결 아이디어 :
그리고 바로 링 노드에 단계보다 더에 질문 위치를 확인합니다. 두 가지 방법 :
해시 테이블 :
해시 테이블만큼 발견 노드는 노드가 존재하고있다 추가 할 때, 증거 원형 연결리스트가있다. 그리고 기존의 노드는 진입 지점입니다
이중 포인터 :
그는 이해할 수 있도록지도를 그린 :
처음부터 목록 트래버스 빠르고 느린 두 손 노드, 노드 2의 빠른 속도, 하나의 노드 느린 속도 :
때 만났다는 :
느린 노드를 이동a+b
때문에 포인터의 2 배 느린 포인터의 빠른 속도의 빠른 노드를 이동 :2(a+b)
느린 노드 노드보다 빠르게 그냥 링 노드 노드 속도 만남 산책합니다. 빠른 노드를 이동(a+b)+(b+c)
열 방정식 :2(a+b)=(a+b)+(b+c)
에 대한 해결 a=c
즉 : 노드가 유입 노드 동일한 길이의 입구 노드에 길이와 헤드 노드를 충족하기 위해
이 시점에서 목록을 통과 계속 헤드 노드 노드 느리거나 빠른 노드가 다른 노드가 만남에 남아 있고, 속도가 1이되도록 경우가 결론을 내릴 수있다, 노드는 다시 이중 포인터 입구 노드를 충족하기 위해 발생 .
참고 : 노드 B의 속도가 충족해야 할 때 이해를 돕기 위하여는, 길이의 상단 절반 부분의 폭 (B)는 실제로 노드리스트 환상의 바이 패스의 전체 길이를 느리게
해시 테이블 문제 해결 :
자바:
public class Solution {
public ListNode detectCycle(ListNode head) {
if (head == null) return null;//如果是空链表直接返回
Set<ListNode> nodeSet = new HashSet<>();//构造哈希表
while (head.next != null) {//链表下一个不为空
if (nodeSet.contains(head)) return head;//哈希表包含该节点则存在环形链表
nodeSet.add(head);//加入节点
head = head.next;//下移一位
}
return null;
}
}
파이썬 :
class Solution(object):
def detectCycle(self, head):
"""
:type head: ListNode
:rtype: ListNode
"""
if head is None:
return None
hashSet=set()#构造集合
while(head.next is not None):
if head in hashSet:#是否已存在
return head
hashSet.add(head)
head=head.next
return None
더블 포인터 문제 해결 :
자바:
public class Solution {
public ListNode detectCycle(ListNode head) {
if (head == null || head.next == null) {
return null;
}
ListNode slow = head;
ListNode fast = head;
while (fast != null && fast.next != null) {//快指针及其下一位是否为null
slow = slow.next;
fast = fast.next.next;
if (slow == fast) {//如果相同,存在环形链表
slow = head;//指向头节点
while (slow != fast) {//继续遍历,再次相遇时的节点即为入环节点
slow = slow.next;
fast = fast.next;
}
return slow;
}
}
return null;
}
}
파이썬 :
class Solution(object):
def detectCycle(self, head):
"""
:type head: ListNode
:rtype: ListNode
"""
if head is None or head.next is None:
return None
slow, fast = head, head
while fast is not None and fast.next is not None:
slow, fast = slow.next, fast.next.next
if slow == fast:
slow = head
while slow != fast:
slow = slow.next
fast = fast.next
return slow
return None
공공 우려 번호에 오신 것을 환영합니다 : 사랑 버그 쓰기 (ID : iCodeBugs)