There are at least two other solutions.
An O(n^2) solution is to keep track of the node numbers. At each node, go back to the head and count how many next
operations it takes to reach the current node. If you get to the nth node before you do n next
operations, then there's a loop in your list. That is:
// assuming head is not null, and head doesn't point to itself
nodeNumber = 1
current = head.next
while (current != null)
{
p = head
counter = 0
while (p != current && counter < nodeNumber)
{
p = p.next
counter = counter + 1
}
if (p != current)
there's a loop
nodeNumber = nodeNumber + 1
}
A destructive method is to reverse the links as you go. If there's a loop in the linked list, then when your pointer is equal to null it will be at the root. That is:
if (head == null) || (head.next == null)
no loop
prev = head
current = head.next
while (current != null)
{
// save next position
next = current.next
// reverse the link
current.next = prev
// and move to the next node
prev = current
current = next
}
if (prev == head)
there is a loop
That does have the disadvantage of destroying the list if there's a loop in it. If there's not a loop, you can go back through the list and reverse the links.