This is a perfect example of a case where the common convention of only ever returning from one point in the function greatly complicates the code.
bool CheckForLoop(Node *head)
{
Node *node1 = head, *node2 = head;
while (node2 && node2->next)
{
node1 = node1->next;
node2 = node2->next->next;
if (node1 == node2)
return true;
}
return false;
}
This is sufficient checking because:
- node1 follows in the path of node2, so if node2 is valid, node1, which refers to an earlier element of the list than node2, must also be valid.
- node1 will never be set to NULL because if the list only has one element, the loop will never execute, and if the list has 2 or more elements, node2 or node2->next will become NULL first.
- If node2 is the last node in the list, then the while condition will evaluate to false.
- If the node after node2 is the last node in the list, then node2 will be assigned a NULL reference. This will never be equal to node1 in the if condition, because node1 is never set to NULL.