Angular 查看与 ng-app/ng-controller 在 DOM 中的展示位置相关的性能

Angular view performance related to ng-app/ng-controller placement in DOM

我想知道如果我将 ng-appng-controller 属性位置从即 body 到一些具有更小 DOM 子树的内页块元素?

假设我有一个很长的页面,包含大量内容,但只有一部分是 Angular 供电的。其他一切都是服务器生成的,这意味着它在客户端 PoV 中有些静态。

ng-app/ng-controller 仅放在 Angular 实际执行的子节点上会更好,还是将它们放在这个非常长的页面的 body 元素上是否相同?

Angular 只处理定义了 ng-app/ng-controller 的子 DOM 的视图,还是处理整个 DOM?

是否有关于此甚至 Angular 文档的任何证据?

Official docs 表示只编译包含在 ng-app 指令中的部分。

If the ng-app directive is found then Angular will:

  • load the module associated with the directive.
  • create the application
  • injector compile the DOM treating the ng-app directive as the root of the compilation. This allows you to tell it to treat only a portion of the DOM as an Angular application.

这是非常符合预期的,因为 Angular 允许多个 Angular 模块控制一页的独立部分(需要手动 bootstrapping,正如 Josiah Keller 在评论中指出的那样)。而且它们的范围不会干扰。

然而,添加额外的静态 html(不是 angular 绑定)只会影响 bootstrap 的性能。是的,angular 必须编译 bootstrap 处的所有元素,以了解以后是否应该处理它们。
但是 运行 时间性能主要受 $watchs 影响。创建它们的隐式形式是进行绑定。因此,您拥有的绑定越多,每个 $digest 周期花费的时间就越长。并给人一种慢应用的普遍感觉。对于现代 browser/CPUs

,我已经达到 2k 手表的合理门槛

ng-app 实际上只是指定 Angular 调用 angular.bootstrap 的根元素。 bootstrap 启动一个 "compilation" 进程,也就是说它遍历根子树中的每个 DOM 元素并从中收集指令并链接它们。

就在那里,您可以看到将应用程序限制在 DOM:

的较小子树中的好处
  1. 编译过程稍快
  2. 编译的指令较少(例如 <input> 不应该成为应用程序一部分的元素不是 compiled/linked)。

要记住的是,$digest 循环是优化性能 problems/opportunities 的重要来源 - 即 $watchers 的数量和 [=15] 的速度=] 是。

Theoretically/Potentially? 是的,正如 New Dev 提到的那样,bootstrap 函数将具有更大的 DOM 到 运行 compile 上,这比编译较小的树需要更长的时间。

实际上?可能不是。但最好的办法是对自己的页面进行基准测试。

作为实验,您可以尝试以下操作。我生成了一个简单的随机 DOM 并将其注入到 JSFiddle 中 console.time 从脚本加载开始,到控制器准备就绪时结束。在更大的 5000 节点树旁边(作为兄弟)有一个小 sub-tree。

这里是 fiddle 包装整个 body:http://jsfiddle.net/gruagq8d/

这里是 fiddle,其中只使用了一小部分:http://jsfiddle.net/h0hod2j8/

对我来说,运行ning 中的任何一个 fiddles 都在大约 260 毫秒内反复收敛。

我也试过 运行在真实的网页源上使用类似的代码,例如 Whosebug 本身,并发现了相同的结果(但是我没有发布任何这些,因为将其他人的真实页面发布到 JSFiddle未经许可感觉不合适) - 您可以自己尝试一下。

诚然,这并没有遵循很好的基准测试方法,但是如果包装大量额外的 DOM 节点会导致显着不同的性能,我仍然期望至少 一些 这些的区别。

我不认为额外的编译时间是个问题;对于小 DOMs 它显然很快,对于大 DOM 与浏览器首先构建 DOM 所花费的时间相比非常相关。

综上所述,如前所述,您最好的选择是尝试 运行 与您自己的页面进行类似的基准测试。

编辑:修改相同的基准测试摘要周期表明它们之间也没有显着差异:

最小包装:http://jsfiddle.net/fsyfn1ee/

环绕整个DOM:http://jsfiddle.net/04tdwxhp/