我知道ng-show和ng-hide影响元素的类集,并且ng-if控制元素是否作为DOM的一部分呈现。
有没有选择ng-if而不是ng-show或ng-hide的指导方针?
- ng if和ng show/ng hide之间的区别可能是什么
- 与DART语言无关。
取决于您的用例,但要总结区别:
ng-if将从dom中删除元素。这意味着所有附加到这些元素的处理程序或任何其他内容都将丢失。例如,如果将click处理程序绑定到某个子元素,当ng-if的计算结果为false时,该元素将从dom中删除,并且您的click处理程序将不再工作,即使在ng-if之后的计算结果为true并显示该元素。您需要重新附加处理程序。
ng-show/ng-hide不从dom中删除元素。它使用CSS样式隐藏/显示元素(注意:您可能需要添加自己的类)。这样就不会丢失附加到孩子身上的处理程序。
ng-if creates a child scope while ng-show/ng-hide does not
与ng-show/ng-hide相比,不在dom中的元素对性能的影响较小,并且您的web应用程序在使用ng-if时可能更快。根据我的经验,两者之间的差别是微不足道的。在使用ng-show/ng-hide和ng-if时,动画是可能的,在角度文档中都有示例。
最后,您需要回答的问题是是否可以从DOM中删除元素?
- 可以将CSS3动画与ng-if一起使用。检查动画段落和文档中的示例。同样,对于ng-hide/ng-show,像:first-child或:nth-child这样的css选择器也不能正常工作,因为隐藏的元素也会被计算在内。
- angular.dart中的动画服务相对较新。在写这篇文章的时候,它是不可用的。
- 如果您使用指令(如ng-click)来绑定处理程序,那么第一点是没有问题的,因为您应该这样做。
- 总结:除非有理由不使用,否则始终使用ng-if。
- 屏幕阅读器和其他辅助技术如何解释用CSS隐藏的DOM元素?如果隐藏元素的原因不仅仅是为了视觉效果,那么我认为ng是合适的选择。此外,刚刚遇到这个问题,与ng相关的范围问题可能需要更多的工作。
- 另外,ng-if创建了一个新的范围,而ng-show没有。
- 还应该指出的是,如果频繁地从DOM中添加和删除元素,会导致高性能成本。
- @ KevinC。同意,但在某种程度上似乎确实存在一种权衡。如果在ng hidden dom元素中有大量的表达式(即观察者),该怎么办?你的消化周期会拉长你的观察者,这会影响整体性能。你同意这种权衡吗?
- @勒克斯,没错。在优化应用程序时,需要考虑所有这些因素。
- plnkr.co/edit/gyybfdzqomcipizzx0xe?p=preview ng if将附加处理程序auto。
- 与ng-if建立新范围的影响是什么?真的有什么变化吗?
- 应该注意的是,执行ng-if的优先级高于ng-show/ng-hide。所以,如果你对一些不够快的显示/隐藏的东西有问题,可以尝试一下ng-if。
- 此外,使用ng show if a child element is required="true",即使它不可见,也需要它。
- 假设我在一个DIV中有很多绑定,并且这些绑定只有在DIV可见时才有意义。那么Ng如果应该有更好的表现……对吗?
- @如果你不小心被发现,拥有一个新的范围会导致一个痛苦的世界:)它打破了双向绑定!
- 我想说这也取决于元素被切换的频率。如果它很少切换,我宁愿选择if,因为处理程序不再需要监视事件。但是(我认为这是更重要的事实):如果经常切换,我更喜欢显示,那么通过CSS隐藏一个元素要比从DOM中删除和附加它便宜得多,尤其是专用的处理程序。
请参阅此处获取一个代码笔,它演示了ng if/ng显示如何工作的差异,以及dom-wise。
@马尔可夫卡萨诺维奇很好地回答了这个问题。但我从另一个角度来看:我总是使用ng-if并从dom中获取这些元素,除非:
出于某种原因,您需要元素上的数据绑定和$watches,以便在它们不可见时保持活动状态。如果您希望能够检查当前不可见的输入的有效性,那么表单可能是一个很好的例子,以确定整个表单是否有效。
正如上面提到的,您使用的是一些非常复杂的状态逻辑和条件事件处理程序。也就是说,如果您发现自己手动附加和分离处理程序,从而在使用ng-if时丢失了重要状态,那么您可以问问自己,在数据模型中是否更好地表示该状态,并且每当呈现元素时,处理程序都有条件地由指令应用。换句话说,处理程序的存在/不存在是状态数据的一种形式。将数据从DOM中取出并放入模型中。处理程序的存在/不存在应由数据决定,因此易于重新创建。
角度写得很好。考虑到它的作用,它很快。但它所做的是一系列的魔法,使困难的事情(如双向数据绑定)看起来非常简单。使所有这些事情看起来简单需要一些性能开销。您可能会惊讶地发现,在没有人看到的一大块DOM上,一个setter函数在$digest周期中被评估了成百上千次。然后你意识到你有几十或数百个不可见的元素都在做同样的事情…
台式机可能确实足够强大,可以使大多数JS的执行速度问题不受影响。但是,如果你正在开发手机,那么只要人类有可能,使用ng应该是一个很简单的方法。JS速度在移动处理器上仍然很重要。使用ng if是一种非常简单的方法,可以以非常、非常低的成本获得潜在的显著优化。
- 上面的答案很好。有一些好的背景,这也有助于决策。谢谢。
- ng-show在你有标签的时候很有用,比如每个标签都有很多需要时间呈现的内容。在第一次呈现之后,标签之间的移动将是即时的,而ng-if将需要重新呈现、绑定事件等。如您所说,缺点是创建在后台执行的监视。Angular非常需要ng-ifshowwatch
根据我的经验:
1)如果您的页面具有使用ng if/ng show显示/隐藏某些内容的切换,则ng if会导致更多浏览器延迟(较慢)。例如:如果您有一个按钮用于在两个视图之间切换,则ng-show似乎更快。
2)当评估为真/假时,ng if将创建/销毁作用域。如果有一个控制器连接到ng if,那么每次ng if的计算结果为true时,都会执行该控制器代码。如果使用ng show,则控制器代码只执行一次。因此,如果您有一个按钮可以在多个视图之间切换,那么使用ng if和ng show将在编写控制器代码的方式上产生巨大的差异。
- 真是太棒了!如果不一定让你的前端更快。这取决于你的需要。事实上,如果您在错误的情况下使用,它可能会反过来。
- 但据我所知,ng如果不渲染到dom上,所以它比ng show/hide快。我错了吗?请让我在那一点上改正。
- ng如果计算结果为false,那么速度会更快,因为正如您所说,不需要将任何内容插入到DOM中。但是,如果这是真的,那么您就有一个将元素(可能相当复杂)插入到DOM中的开销。
- 这真是个好消息!
- "2)当评估结果为真/假时,ng if将创建/销毁作用域。如果您有一个连接到ng if的控制器,则该控制器代码将在每次
答案并不简单:
它取决于目标机器(移动与桌面),取决于数据的性质,浏览器,操作系统,运行的硬件…如果你真的想知道的话,你需要做基准测试。
这主要是一个内存与计算的问题…与大多数性能问题一样,重复元素(n)类列表的差异可能变得非常显著,尤其是在嵌套(n x n或更糟)时,以及在这些元素中运行的计算类型:
ng-show:如果这些可选元素经常出现(密集),比如说90%的时间,准备好它们并只显示/隐藏它们可能会更快,尤其是当它们的内容很便宜时(只是纯文本,不需要计算或加载)。这会消耗内存,因为它用隐藏的元素填充DOM,但是只显示/隐藏已经存在的内容对于浏览器来说可能是一个便宜的操作。
ng-if:如果相反,元素很可能不会显示(稀疏),那么只需实时构建并销毁它们,尤其是当它们的内容很昂贵时(计算/排序/过滤、图像、生成的图像)。这是稀有元素或"按需"元素的理想选择,它可以节省内存,而不会填充DOM,但会花费大量的计算(创建/销毁元素)和带宽(获取远程内容)。它还取决于您在视图中计算的量(过滤/排序)与您在模型中已经拥有的量(预先排序/预先过滤的数据)。
- 技术事实的其他答案。这是为了智慧。您已经清楚地构建了非平凡的角度应用程序,先生!+ 1
- 这个问题超出了角度,它是计算机科学中的一个基本问题,从某个角度来看,一种方法比另一种方法更有效。通常,这可以通过一些基准来发现。所以您甚至可以根据项目计数在一个方法和另一个方法之间切换…类似主题:math.stackexchange.com/questions/1632739/…
一个重要注意事项:
ngif(与ngshow不同)通常创建可能产生意外结果的子作用域。
我有一个与此相关的问题,我花了很多时间来弄清楚到底发生了什么。
(我的指令将其模型值写入了错误的范围。)
所以,如果你跑得太慢,就用ngshow来保存你的头发。
不管怎样,性能差异几乎不明显,我还不确定在没有测试的情况下谁会喜欢它…
- 在ngif内的数据绑定中使用$parent.scopevar可以纠正在使用ngif时出现的子范围问题。
- 这并非完全正确(即@user2173353的原始注释)。如果你坚持好的做法,你就不会陷入麻烦。这是一个非常基本的规则:"如果没有点,你就错了。"请参阅此处以了解它的工作原理:bit.ly/1spv4wl。另一个很好的参考(参见错误2):bit.ly/1qffewd>(我的指令是将其模型值写入错误的范围。)这是不遵守上述实践的结果。
- @piotr.d You are right, but that is not something a beginner may need to focus on and there is another best practice that says that it is better to leave performance improvements for the end (especially performance improvements that may not be improvements in reality). 我见过有人把ngIf放在任何地方,认为这会提高性能。这是完全不正确的,如果没有对特定情况的测试或深入分析,就不能说哪一个是最好的,ngIf或ngShow。所以,我还是建议你在看到糟糕的表现或知道自己在做什么之前,不要再去想ngIf。
- 好点。但是使用Controlleras使这成为一个没有问题的问题。例如,参见约翰·帕帕对控制器和虚拟机的看法。
如果使用ng-show or ng-hide,则无论表达式的值如何,都将加载内容(例如来自服务器的缩略图),但将根据表达式的值显示内容。
如果使用ng-if,只有当ng if的表达式计算为truthy时,才会加载内容。
在将要从服务器加载数据或图像并仅根据用户交互显示这些数据或图像的情况下,使用ng-if是一个好主意。这样页面加载就不会被不必要的nw密集型任务阻塞。
- 这尤其有用,因为即使CSS隐藏了它们的DOM容器,大多数浏览器也会加载图像。他们通常只是在加载img标记时查找src属性!
ng如果在ng上包括和在ng控制器上会有很大的影响。在ng include上,它不会加载所需的部分,除非标志为true,否则不会处理。在NG控制器上,除非标志为真,否则不会加载控制器。但问题是,当一个标志在ng中变为假时,如果它在flag变为真时从dom中移除,它将重新加载dom,在这种情况下,ng show更好,一次性show ng if更好