4

是否可以动态扩展javascript函数范围?我尝试了以下但没有成功:

function foo()
{
    var bar = 12;
    return function(x)
    {
        return eval(x);
    }
}

var e = foo();

console.log(e("bar"));           // 12
console.log(e("bar = 42;"));     // 42
console.log(e("bar"));           // 42
console.log(e("var baz = 99;")); // undefined
console.log(e("baz"));           // ReferenceError: baz is not defined

但是,如果我var从该行中删除,baz = 99则 baz 变量将变为全局变量(这对我来说非常有意义):

...
console.log(e("baz = 99;"));     // 99
console.log(e("baz"));           // 99
console.log(baz);                // 99 (so baz is just a global)
4

3 回答 3

1

每次调用e("var baz = 4")时,它都会在该函数调用的堆栈上创建一个变量,因此下次调用它时它将不可用。

如果您需要将变量动态添加到范围,我会使用 Rayno 的建议,使用地图。http://jsfiddle.net/UVSrD/

function foo()
{
    var scope = {};
    return function(x)
    {
        return eval(x);
    }
}


var e = foo();

console.log(e("scope.bar = 12")); // 12
console.log(e("scope.bar")); // 12
console.log(e("scope.baz = 14")); // 14
console.log(e("scope.baz;")); // 14
// Not a global
console.log(typeof scope) // undefined
于 2012-04-03T20:00:10.937 回答
0

您正在使用以下代码创建一个闭包:

function foo()
{
    var bar = 12;
    return function(x)
    {
        return eval(x);
    }
}

当您传入 bar 时,您会覆盖已经启动到 12 的 bar 变量。我不确定您要完成什么,但使用闭包将保留外部函数变量。

于 2012-04-03T19:35:38.780 回答
0

eval 将在它被调用的任何地方运行。您看到的行为是因为在这一行:

console.log(e("var baz = 99;")); // undefined

您在返回函数的本地范围内创建一个 var baz = 99 。var name = value 的返回值;什么都不是,你得到未定义的。当您随后致电时

console.log(e("baz"));           // ReferenceError: baz is not defined

您返回一个未定义 baz 的新函数。

这有点酷:http ://www.bennadel.com/blog/1926-Exploring-Javascript-s-eval-Capabilities-And-Closure-Scoping.htm

于 2012-04-03T19:54:31.080 回答