Detect a Cycle in a Linked List
Problem
Build a linked list from the array. If k is not -1, the last node links back to the node at index k, which creates a cycle. If k is -1, the last node links to nothing. Print true if the list has a cycle, else false. Do not use extra memory that grows with n.
Constraints
- 1 <= n <= 10^5
- -1 <= k < n
Examples
Input
4 3 2 0 -4 1
Output
true
Solutions
Floyd's algorithm: a fast runner and a slow runner. On a straight path the fast runner reaches the end. On a circular track the fast runner laps the slow one, so they meet. It needs only two pointers.
/*
* Problem : Detect a cycle.
* Input : n, the values, and k.
* Output : true or false.
* Approach: Fast and slow pointers.
* Time : O(n)
* Space : O(1)
* Java : 8 or newer.
*/
import java.util.Scanner;
public class Main {
// Step 1: A node holds one value and a link to the next node. The last node links to null.
static class Node {
int value;
Node next;
Node(int value) {
this.value = value;
}
}
// This method solves the task. It receives the input and returns the answer.
static boolean solve(int[] a, int k) {
// Step 2: Build the nodes and link them one after another.
Node[] nodes = new Node[a.length];
for (int i = 0; i < a.length; i++) {
nodes[i] = new Node(a[i]);
if (i > 0) {
nodes[i - 1].next = nodes[i];
}
}
// Step 3: If k is not -1, link the last node back to the node at index k.
if (k >= 0) {
nodes[a.length - 1].next = nodes[k];
}
// Step 4: Two pointers. slow moves 1 step and fast moves 2 steps. In a cycle, fast catches slow.
Node slow = nodes[0];
Node fast = nodes[0];
while (fast != null && fast.next != null) {
slow = slow.next;
fast = fast.next.next;
if (slow == fast) {
return true;
}
}
// Step 5: fast reached the end of the list, so there is no cycle.
return false;
}
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int size = scanner.nextInt();
int[] a = new int[size];
for (int i = 0; i < size; i++) {
a[i] = scanner.nextInt();
}
int k = scanner.nextInt();
System.out.println(solve(a, k));
}
}
Hints (2)
- What happens if fast reaches null?
- Why must they meet inside a cycle?