tags:

views:

147

answers:

3

hello everyone I'm trying to find this algorithm on c++ in net but can't, I found this one

// Best solution
function boolean hasLoop(Node startNode){
  Node slowNode = Node fastNode1 = Node fastNode2 = startNode;
  while (slowNode && fastNode1 = fastNode2.next() && fastNode2 = fastNode1.next()){
    if (slowNode == fastNode1 || slowNode == fastNode2) return true;
    slowNode = slowNode.next();
  }
  return false;
}

but doesn't seem to be right, or am I wrong? how can I actually prove that my hare will meet turtose at the end? tranks in advance for any explanation how exactly does it work and proof

EDITED

about this solution, I found that in regular algorithm they use only one fast iterator but here they use two, why?

A: 

This algorithm will find a cycle in a linked list.
one fast node can be used instead:

 function boolean hasLoop(Node startNode){
  Node slowNode = Node fastNode = startNode;
  while (slowNode && fastNode = fastNode.next() && fastNode = fastNode.next()){
    if (slowNode == fastNode) return true;
    slowNode = slowNode.next();
  }
  return false;
}
Itay
+1  A: 

The idea in the code you've found seems fine. Two fast iterators are used for convenience (although I'm positive such kind of 'convenience', like putting a lot of 'action' in the condition of while loop, should be avoided). You can rewrite it in more readable way with one variable:

while (fastNode && fastNode.next()) {
    if (fastNode.next() == slowNode || fastNode.next().next() == slowNode) {
        return true;
    }
    fastNode = fastNode.next().next();
    slowNode = slowNode.next();
}
Nikita Rybak
the problem with `fastNode.next().next()` is that the first next may return null
Itay
@Itay nope, it's checked in the loop condition
Nikita Rybak
Right - i missed it. :)
Itay
+1  A: 

The algorithm is correct. Proof:

The case of no cycle is trivial: the hare will find the end of the list.

So, there's a cycle, and the hare enters it, running around like crazy. Eventually, the tortoise reaches the first node of the cycle. From this point on, both necessarily stay in the cycle: the only way they can go from a node is to the next node, which eventually leads back to the first node of the cycle. (Draw a picture of the list/graph to convince yourself.)

Since the hare moves faster, it will eventually catch up with the tortoise. Depending on the length of the cycle and the number of nodes traversed before entering it (whether they are odd or even is what matters, so there are four cases), this may happen after an odd or an even number of steps. That's why the hare should check both its current node and the next node for the tortoise's presence. (The example code uses two pointers to achieve this, though that's not really necessary.)

For a more formal proof, check out this Wikipedia page.

larsmans