Search code examples
javascriptfunctionmutual-recursion

simple javascript function definition problem


function First () {
setTimeout("Second()", 50)
};

function Second () {  //I'm very confident this conditional works fine
 if  (document.getElementsByClassName("l")[0].href ==
      document.getElementById("myFrame").getAttribute("src"))  
   {  
   First();                                       
   }
 else
   {
   var newLink = document.getElementsByClassName("l")[0].href;        //
   document.getElementById("myFrame").setAttribute("src", newLink);
   }};

First ();

The problem is that when First() is defined, I get the error that Second isn't defined. How can this be solved?


Solution

  • Update

    Your updated code is quite different from your original code. The problem appears to be the string you're passing to setTimeout (which surprised me, but was easily replicated). I would change

    function First () {
        setTimeout("Second()", 50)
    };
    

    to

    function First () {
        setTimeout(Second, 50);
    }
    

    ...or if you need to pass parameters to Second:

    function First() {
        setTimeout(function() {
            Second(param0, param1);
        }, 50);
    }
    

    (Note that there's no need for a ; at the end of a function declaration, but one after the setTimeout wouldn't go amiss [you don't actually need it, the horror that is "semicolon insertion" will insert it for you in this case, but...].)

    The second and third versions above use a function reference. Your original uses a string which is then compiled, which is unnecessary and appears to be the problem (as this example using the string fails, but this one with the function reference works).

    Original Answer

    As of the answer below, the code quoted in your question was:

    function First() {Second();};
    function Second() {First();};
    

    That code will work just fine. It's an infinite loop (well, not infinite, because eventually the implementation won't have any more stack space for return addresses), but until it blows up because of that it'll work fine. Example

    It will fail if your actual code looks more like this:

    var First = function() {
        Second();
    };
    First();
    var Second = function() {
        First();
    };
    

    ...because that's very different, it uses function expressions (which are processed as part of the step-by-step code) rather than function declarations (which are processed upon entry to the scope, before any step-by-step code) and it has a call to First before Second is defined. See this other answer here on StackOverflow for more detail on the distinction between a function expression and a function declaration.