开发者

How can I execute recursion regardless of the function name? [duplicate]

This question already has answers here: 开发者_开发问答 Closed 11 years ago.

Possible Duplicate:

Can I get the name of the currently running function in javascript?

I need this for recursion. I'd like to be able to change the function name without checking and changing every instance where the function calls itself.

(For example php has "magic constants" like __FUNCTION__ etc.. - is something similar in JavaScript?)


If your goal is recursion, you don't need the function name as a string if you can get a reference to the function itself. Note that you'll still have to check and change every instance where the function is called by others, and that's likely to be a larger task than updating the recursive calls (if for no other reason than it's not localized to the function body).

Passing the function as an argument

function foo(self, i)
{
    if (i === 0 )
        return;

    console.log(i--);
    self(self, i);
}

foo(foo, 3);

Using arguments.callee (As Raynos points out, this is brittle in strict mode)

function foo(i)
{
    if (i === 0 )
        return;

    console.log(i--);
    arguments.callee(i);
}

foo(3);

Output of either option

3
2
1


Maybe you can refactor your function since arguments.callee is not dependable. For example, you could use a nested function that does the recursion:

var name_does_not_matter = function(m) {
    var inner = function(n) {
        if (n <= 2) return 1;
        return inner(n-2) + inner(n-1);
    };
    return inner(m);
};

[UPDATE] Actually, you should be able to access the function by its name regardless of the parent scope. In my test, the following example works:

var foo = 10;
var bar = function foo(n) {
    return (n <= 2) ? 1 : foo(n-2) + foo(n-1);
};
alert(foo);  // Displays '10'
alert(bar(10));  // Displays '55'


function senad()
{
  var fName= arguments.callee.toString();
            fName= fName.substr('function '.length);       
            fName= fName.substr(0, fName.indexOf('('));  
            alert(fName)
}
senad();


(function() { 
  "use strict"; 
  console.log(arguments.callee); 
})()

Yields

TypeError: Cannot access property 'callee' of strict mode arguments

You cannot do this in ES5 strict mode, and for a good reason. It's a hack. Don't do it.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜