我想将js arguments.callee替换为另一个符号,例如 SELF

可能吗?

sweetjs这样的宏方法是唯一的方法吗?

编辑

非常感谢您的投入:

我了解arguments.callee在StrictMode中被禁止。

为了清楚起见,我介绍一下我的代码:匿名递归

var factorial = function (n)
{
    return n ? n * arguments.callee(n - 1) : 1;
};
console.log( factorial(10) );  //3628800

现在
var SELF = function (val)
{
    return arguments.callee(val);
}
var factorial = function (n)
{
    return n ? n * SELF(n - 1) : 1;
};
console.log( factorial(10) );

给出一个错误
var SELF = function (val)
                    ^
RangeError: Maximum call stack size exceeded

另外,我知道匿名递归有一种方法不使用arguments.callee,而是使用 Y-Combinator

但是,arguments.callee不能用这种正确的东西代替吗?
Y-Combinator 方案中,代码必须为
var f = function(f) {
           return function(n){
              return n ? n * f(n - 1) : 1;
           }
        }

嵌套变得更深,以定义阶乘等,我不愿意...

EDIT2

短时间后,出现了一篇精美的文章。

Anonymous recursion in 6 lines of Javascript

作者Arne Martin称 z-combinator :
var Z = function(func)
{
    var f = function ()
    {
        return func.apply(null, [f].concat([].slice.apply(arguments)));
    };
    return f;
}

var factorial = function (f, n)
{
    return n ? n * f(n - 1) : 1;
}

console.log(  Z(factorial)(10) );

这种方法完全可以满足我的需求,而且由于它不需要'arguments.callee',因此我们不必担心严格的模式!

最佳答案

如果您不想使用严格模式,并且不介意使用全局变量和不建议使用的功能,则可以向大多数现代JS实现中添加自定义只读“关键字”:

Object.defineProperty(
 self,
 "SELF",
 {get:function(){return arguments.callee.caller;} //!! deprecated feature in use!!
});


function demo(a,b){
  alert(SELF);
}

function someOtherFunction(a,b){
  alert(SELF);
}



demo();
someOtherFunction();

这很酷,但是还有更健壮和现代的方法可以做到这一点,即使用函数名:
function someAdditionalFunction(a,b){
  alert(someAdditionalFunction);
}

使用名称,您可以获取与上面的“SELF” getter相同的信息,并且可以在严格模式下使用,而没有全局变量。使用函数名称的一个缺点是,除非您使用专门命名的函数表达式,并且不能给函数和内部名称self,否则不能一再重复使用相同的符号:
var demo=function SELF(a,b){
  alert(SELF);
};

var someOtherFunction=function SELF(a,b){
  alert(SELF);
};

demo();
someOtherFunction();

关于javascript - 匿名递归-是否可以将javascript 'arguments.callee'替换为其他符号(例如 'SELF')?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/17645356/

10-09 15:04