【问题标题】:This in Private context这在私人环境中
【发布时间】:2013-03-23 03:26:56
【问题描述】:

我想访问在私有上下文中创建的变量。我正在创建一个这样的私有上下文:

(new Function("var a = 'hello'; console.log('this', this);")).call({});
// outputs -> this Object {}

我在 call'ing 使用空上下文的函数。但是this 不包含a 变量。无论如何,console.log 怎么可能在空上下文中工作?

【问题讨论】:

  • 为什么不直接调用 console.log('this', a); ?
  • 因为我想访问在上下文中创建的所有变量。

标签: javascript variables object scope private


【解决方案1】:

jsFiddle Demo

存在创建对象var a 的函数的范围内。但是,一旦该范围丢失,变量也会丢失。如果您希望 a 持续存在,则需要将其附加到使用 this 关键字创建的对象:

(new Function("this.a = 'hello'; console.log(this);")).call({});

但是,这是一种混淆的方式。这里有一些不需要的元素。主要是不需要new 关键字(Function 表示函数对象)。 Function还自带方法,比如call

Function("this.a = 'hello'; console.log(this);").call({});

这也可以。此外,如果您想保留变量 a 中的内容,您可以随时这样做 (demo):

var obj = {};
Function("this.a = 'hello'").call(obj);
obj.a;//hello

至于为什么它适用于空上下文。您实际上已经使用{} 给了它一个新构造的对象。这就是遇到引用this 时在函数内部使用的范围。事实上,如果您不打算使用作用域,call() 不需要参数。像这样的:

Function("console.log(5);").call();

5 无错误地记录到控制台。


您的问题中使用的方法是从魔术字符串构建一个函数。我必须说,这种方法非常酷,与 eval 非常相似。但你正在寻找的归结为我认为的这种差异:

function ball(){
 var color = "red";
 return color;
}

function Ball(){
 this.color = "red";
}

console.log(ball());//logs red
console.log(new Ball().color);//logs red

【讨论】:

  • 只是一个小细节。由于您不存储对空对象的引用,因此您也永远无法通过这种方式访问​​ a 变量。
  • @HoLyVieR - 它在日志上显示为对象上的存在。确实,该对象的唯一作用域是在这一行中,因此将来不会有可用的访问权限,并且整个混乱在执行后将有资格进行垃圾收集。
  • 即使我附加了父上下文,我仍然无法获得a,这是怎么回事? (new Function("var a = 'hello'; console.log(this.a);")).call(this); 返回未定义
  • @Adam - this.avar a 之间存在差异。如果您要使用console.log(a),则会记录hello
  • 是的,但我这样做的全部原因是要有一个对象来保存我在上下文中创建的变量。
猜你喜欢
  • 2019-04-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-09-15
  • 1970-01-01
  • 2012-03-30
  • 2012-02-27
  • 1970-01-01
相关资源
最近更新 更多