本文介绍了Javascript:为什么对闭包变量的访问可能很慢的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我最近阅读了这篇,并对避免使用关闭的陷阱建议感到困惑(似乎这些建议是针对变量范围是动态的CommonLisp用户提供的):

Recently I've read this performance guide Let's make the web faster and was puzzled by "Avoiding pitfalls with closures" recommendations (as if these advices were given for CommonLisp users where variable scoping is dynamic):

var a = 'a';
function createFunctionWithClosure() {
  var b = 'b';
  return function () {
    var c = 'c';
    a;
    b;
    c;
  };
}

var f = createFunctionWithClosure();
f();



a 慢于引用 b ,这比引用 c 。

when f is invoked, referencing a is slower than referencing b, which is slower than referencing c.

很明显,引用局部变量 c em> b ,但如果iterpreter正确写入(没有动态范围 - 类似链接散列表查找...),速度差异应该只是边际。还是不?

It's quite evident that referencing local variable c is faster than b, but if the iterpreter is written properly (without dynamic scoping - something like chained hashtable lookup..) the speed difference should be only marginal. Or not?

推荐答案

你说得对。现代JS引擎将优化范围链查找和原型链查找很多。方法,AFAIK引擎trs保存某种哈希表与下面的访问节点。

You're right. Modern JS engines will optimize the scope chain lookup and the prototype chain lookup like a lot. Means, AFAIK the engine trys to hold some sort of hash-table with access nodes underneath.

这只有当没有 eval() (显式或隐式,例如 setTimeout )或 try-catch c $ c> a with语句被调用。由于这样的结构,解释器不能确定如何访问数据,它需要fallback到经典的范围链查找这真的意味着,它必须爬取所有父上下文变量/激活对象并尝试解析搜索的变量名称。
当然,这个过程对于位于远离开始查找处的对象/名称将需要更多的时间。这又意味着访问全局对象上的数据总是最慢的。

This only works if there is no eval() (explicity or implicitly, e.g. setTimeout) or a try-catch clause or a with statement invoked. Because of such constructs, the interpretator can't be sure about how to access data and it needs to "fallback" into a classical scope chain lookup which really means, it has to crawl through all parent context variable / activation objects and try to resolve the searched variable name.This process of, of course, will take more time for objects/names which are located "far away" from where the lookup processed was started. That in turn means, that accessing data on the global object will always be the slowest.

在您的代码片段中, a 的查找过程将像

In your snippet, the lookup process for a would go like

anonymous function -> Execution Context -> Activation Object (not found)
anonymous function -> Execution Context -> [[ Scope ]] 
    - createFunctionWithClosure
    - global scope
createFunctionWithClosure -> Activation Object (not found)
global scope -> Variable Object (found)






这篇关于Javascript:为什么对闭包变量的访问可能很慢的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-26 12:37