在链表中查找循环的长度
编写一个函数detectAndCountLoop()来检查给定的链表是否包含循环,如果存在循环,则返回循环中节点的计数。例如,循环存在于下链表中,循环长度为 4。如果不存在循环,则函数应返回 0。
方法:众所周知,当快慢指针在公共点相遇时,弗洛伊德循环检测算法终止。众所周知,该公共点是循环节点之一。将这个公共点的地址存储在一个指针变量中,比如 (ptr)。然后用 1 初始化计数器并从公共点开始,继续访问下一个节点并增加计数器,直到再次到达公共指针。
此时,计数器的值将等于循环的长度。
算法:
- 使用 Floyd's Cycle 检测算法找到循环中的公共点
- 将指针存储在临时变量中并保持计数 = 0
- 遍历链表直到再次到达同一节点并在移动到下一个节点时增加计数。
- 将计数打印为循环长度
C++
// C++ program to count number of nodes
// in loop in a linked list if loop is
// present
#include
using namespace std;
/* Link list node */
struct Node
{
int data;
struct Node* next;
};
// Returns count of nodes present in loop.
int countNodes(struct Node *n)
{
int res = 1;
struct Node *temp = n;
while (temp->next != n)
{
res++;
temp = temp->next;
}
return res;
}
/* This function detects and counts loop
nodes in the list. If loop is not there
in then returns 0 */
int countNodesinLoop(struct Node *list)
{
struct Node *slow_p = list, *fast_p = list;
while (slow_p && fast_p &&
fast_p->next)
{
slow_p = slow_p->next;
fast_p = fast_p->next->next;
/* If slow_p and fast_p meet at
some point then there is a loop */
if (slow_p == fast_p)
return countNodes(slow_p);
}
/* Return 0 to indeciate that
their is no loop*/
return 0;
}
struct Node *newNode(int key)
{
struct Node *temp =
(struct Node*)malloc(sizeof(struct Node));
temp->data = key;
temp->next = NULL;
return temp;
}
// Driver Code
int main()
{
struct Node *head = newNode(1);
head->next = newNode(2);
head->next->next = newNode(3);
head->next->next->next = newNode(4);
head->next->next->next->next = newNode(5);
/* Create a loop for testing */
head->next->next->next->next->next = head->next;
cout << countNodesinLoop(head) << endl;
return 0;
}
// This code is contributed by SHUBHAMSINGH10
C
// C program to count number of nodes
// in loop in a linked list if loop is
// present
#include
#include
/* Link list node */
struct Node
{
int data;
struct Node* next;
};
// Returns count of nodes present in loop.
int countNodes(struct Node *n)
{
int res = 1;
struct Node *temp = n;
while (temp->next != n)
{
res++;
temp = temp->next;
}
return res;
}
/* This function detects and counts loop
nodes in the list. If loop is not there
in then returns 0 */
int countNodesinLoop(struct Node *list)
{
struct Node *slow_p = list, *fast_p = list;
while (slow_p && fast_p && fast_p->next)
{
slow_p = slow_p->next;
fast_p = fast_p->next->next;
/* If slow_p and fast_p meet at some point
then there is a loop */
if (slow_p == fast_p)
return countNodes(slow_p);
}
/* Return 0 to indeciate that ther is no loop*/
return 0;
}
struct Node *newNode(int key)
{
struct Node *temp =
(struct Node*)malloc(sizeof(struct Node));
temp->data = key;
temp->next = NULL;
return temp;
}
/* Driver program to test above function*/
int main()
{
struct Node *head = newNode(1);
head->next = newNode(2);
head->next->next = newNode(3);
head->next->next->next = newNode(4);
head->next->next->next->next = newNode(5);
/* Create a loop for testing */
head->next->next->next->next->next = head->next;
printf("%d \n", countNodesinLoop(head));
return 0;
}
Java
// Java program to count number of nodes
// in loop in a linked list if loop is
// present
import java.io.*;
class GFG {
/* Link list node */
static class Node
{
int data;
Node next;
Node(int data)
{
this.data =data;
next =null;
}
}
// Returns count of nodes present in loop.
static int countNodes( Node n)
{
int res = 1;
Node temp = n;
while (temp.next != n)
{
res++;
temp = temp.next;
}
return res;
}
/* This function detects and counts loop
nodes in the list. If loop is not there
in then returns 0 */
static int countNodesinLoop( Node list)
{
Node slow_p = list, fast_p = list;
while (slow_p !=null && fast_p!=null && fast_p.next!=null)
{
slow_p = slow_p.next;
fast_p = fast_p.next.next;
/* If slow_p and fast_p meet at some point
then there is a loop */
if (slow_p == fast_p)
return countNodes(slow_p);
}
/* Return 0 to indeciate that ther is no loop*/
return 0;
}
static Node newNode(int key)
{
Node temp = new Node(key);
return temp;
}
/* Driver program to test above function*/
public static void main (String[] args) {
Node head = newNode(1);
head.next = newNode(2);
head.next.next = newNode(3);
head.next.next.next = newNode(4);
head.next.next.next.next = newNode(5);
/* Create a loop for testing */
head.next.next.next.next.next = head.next;
System.out.println( countNodesinLoop(head));
}
}
// This code is contributed by inder_verma.
Python3
# Python 3 program to find the number
# of nodes in looop in a linked list
# if loop is present
# Python Code to detect a loop and
# find the length of the loop
# Node defining class
class Node:
# Function to make a node
def __init__(self, val):
self.val = val
self.next = None
# Linked List defining and loop
# length finding class
class LinkedList:
# Function to initialize the
# head of the linked list
def __init__(self):
self.head = None
# Function to insert a new
# node at the end
def AddNode(self, val):
if self.head is None:
self.head = Node(val)
else:
curr = self.head
while(curr.next):
curr = curr.next
curr.next = Node(val)
# Function to create a loop in the
# Linked List. This function creates
# a loop by connnecting the last node
# to n^th node of the linked list,
# (counting first node as 1)
def CreateLoop(self, n):
# LoopNode is the connecting node to
# the last node of linked list
LoopNode = self.head
for _ in range(1, n):
LoopNode = LoopNode.next
# end is the last node of the Linked List
end = self.head
while(end.next):
end = end.next
# Creating the loop
end.next = LoopNode
# Function to detect the loop and return
# the length of the loop if the returned
# value is zero, that means that either
# the linked list is empty or the linked
# list doesn't have any loop
def detectLoop(self):
# if linked list is empty then there
# is no loop, so return 0
if self.head is None:
return 0
# Using Floyd’s Cycle-Finding
# Algorithm/ Slow-Fast Pointer Method
slow = self.head
fast = self.head
flag = 0 # to show that both slow and fast
# are at start of the Linked List
while(slow and slow.next and fast and
fast.next and fast.next.next):
if slow == fast and flag != 0:
# Means loop is confirmed in the
# Linked List. Now slow and fast
# are both at the same node which
# is part of the loop
count = 1
slow = slow.next
while(slow != fast):
slow = slow.next
count += 1
return count
slow = slow.next
fast = fast.next.next
flag = 1
return 0 # No loop
# Setting up the code
# Making a Linked List and adding the nodes
myLL = LinkedList()
myLL.AddNode(1)
myLL.AddNode(2)
myLL.AddNode(3)
myLL.AddNode(4)
myLL.AddNode(5)
# Creating a loop in the linked List
# Loop is created by connecting the
# last node of linked list to n^th node
# 1<= n <= len(LinkedList)
myLL.CreateLoop(2)
# Checking for Loop in the Linked List
# and printing the length of the loop
loopLength = myLL.detectLoop()
if myLL.head is None:
print("Linked list is empty")
else:
print(str(loopLength))
# This code is contributed by _Ashutosh
C#
// C# program to count number of nodes
// in loop in a linked list if loop is
// present
using System;
class GFG
{
/* Link list node */
class Node
{
public int data;
public Node next;
public Node(int data)
{
this.data = data;
next = null;
}
}
// Returns count of nodes present in loop.
static int countNodes( Node n)
{
int res = 1;
Node temp = n;
while (temp.next != n)
{
res++;
temp = temp.next;
}
return res;
}
/* This function detects and counts loop
nodes in the list. If loop is not there
in then returns 0 */
static int countNodesinLoop( Node list)
{
Node slow_p = list, fast_p = list;
while (slow_p != null && fast_p != null &&
fast_p.next != null)
{
slow_p = slow_p.next;
fast_p = fast_p.next.next;
/* If slow_p and fast_p meet at some point
then there is a loop */
if (slow_p == fast_p)
return countNodes(slow_p);
}
/* Return 0 to indeciate that ther is no loop*/
return 0;
}
static Node newNode(int key)
{
Node temp = new Node(key);
return temp;
}
/* Driver code*/
public static void Main (String[] args)
{
Node head = newNode(1);
head.next = newNode(2);
head.next.next = newNode(3);
head.next.next.next = newNode(4);
head.next.next.next.next = newNode(5);
/* Create a loop for testing */
head.next.next.next.next.next = head.next;
Console.WriteLine( countNodesinLoop(head));
}
}
// This code is contributed by Rajput-Ji
Javascript
输出 :
4
复杂度分析:
- 时间复杂度: O(n)。
只需要对链表进行一次遍历。 - 辅助空间: O(1)。
因为不需要额外的空间。
相关文章:
- 检测链表中的循环
- 检测和删除链表中的循环
如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程和学生竞争性编程现场课程。