【问题标题】:What is the performance cost of maintaining a live HTMLCollection?维护实时 HTMLCollection 的性能成本是多少?
【发布时间】:2018-12-24 18:20:52
【问题描述】:

我的一段前端 JS 代码依赖于数千个 DOM 节点的实时 HTMLCollection。由于它是实时的,它会随着 DOM 的更新而自动更新。

这与我每次修改 DOM 时都重新运行document.getElementsByClassName 调用相同,还是在后台进行了性能优化?

【问题讨论】:

  • 视情况而定。 Murphy 说,如果你真的需要优化,那么它在部署的环境中将不可用。如果您不需要它,那么它将可用。
  • @skyboyer 那篇文章有点误导。 创建一个活动的 NodeList 非常快,因为查找 DOM 元素的开销会延迟到元素被访问。
  • @Barmar 文章同样指出:“浏览器可以更快地创建和返回实时 NodeList 对象,因为它们不必预先拥有所有信息,而静态 NodeList 需要拥有所有从一开始他们的数据。“
  • @skyboyer 是的,它们可以创建得更快,但第一次访问会慢一些。没有免费的午餐。

标签: javascript performance htmlcollection


【解决方案1】:

This blog post 解释了一些静态和实时 NodeLists 之间的区别,并提到了实时集合是如何实现的。

在您访问其元素之前,实时集合不会访问 DOM。那时它会创建实际的集合并缓存它。如果 DOM 不改变,以后的访问不会产生任何开销。

更改 DOM 不应立即更新任何集合。相反,它应该只是使他们的缓存无效。下次您访问其中一个集合时,它将重新生成。

因此,如果您创建一个实时集合并且与 DOM 修改相比不经常访问它,那么开销应该相对较小。最糟糕的情况是,如果您循环访问实时集合并在循环期间修改 DOM——每次迭代都必须更新集合。

可能会有其他优化可以缓解这种情况。对于某些类型的实时集合,JavaScript 引擎可能能够判断特定的 DOM 修改是否会影响它;如果没有,它不必使集合无效。例如,使用document.getElementsByClassName() 创建的集合不会受到不会在任何地方添加或删除指定类的修改的影响。但是,如果您执行删除元素之类的操作,则必须检查该类是否出现在以该元素为首的子树中的任何位置,因此这并不明显比仅仅使缓存无效更好。

【讨论】:

    猜你喜欢
    • 2010-09-20
    • 2015-04-21
    • 2018-02-16
    • 2011-02-12
    • 1970-01-01
    • 2011-06-20
    • 1970-01-01
    • 2017-05-13
    • 2016-08-27
    相关资源
    最近更新 更多