获取脏检查的时机

Angular 使用NgZone获取变化的通知,然后进行全面的变化检测,进而更新Dom

脏检查的过程

Angular的数据流是自顶而下,从父组件到子组件单项流动,单项数据流保证了高效可预测的变化检测。尽管检查了父组件之后,子组件可能会改变父组件的数据使得父组件需要再次被检查,这是不被推荐的数据处理方式。在开发模式下Angular会进行二次检查,如果出现上述情况,二次检查就会报错:Expression Changed After It Has Been Checked Error。而在生产环境中,脏检查只会执行一次。

变化检测策略

Default

通过NgZone代理的每个异步操作的构造函数中,对组件进行全面的脏检查,进而更新显示

OnPush

相比Default只需要在@Component装饰器中加上一句

changeDetection:ChangeDetectionStrategy.OnPush

组件级别的控制,这种模式下,变化检测变的相对严格,不是所有异步操作都会导致组件进行变化检测,这一定程度上保证了程序的性能,但是也给组件的编写增加了复杂性,经常需要自己手动操作变化检测来确保界面及时响应。

隔离当前组件及子组件

组件使用OnPush模式后, 外部执行 (setTimeout、http request、事件、Observable订阅)想触发我组件的变化检测就变得困难,如果确定需要更新界面就需要手动调用变化检测,可以使用markForCheck方法。

外部执行 只有对这个组件中的数据进行修改了,我们才期望变化检测能够检测出数据的变化从而更新组件的显示,这里的外部执行的代码大部分情况下其实是我的组件的内部的代码,只不过因为执行的是异步操作,而这个操作终止时Angular并不知道从哪里开始进行变化检测,所以Angualr开始从组件树的顶层开始向下检查,到达当前组件时发现它属于OnPush模式而数据输入并没有改变所以就不在进行变化检测,所以需要手动调用检查,这也保证了,在其它组件中的异步执行不会触发到当前组件的变化检测(因为根本不相关),从而提高性能。

同步事件 会触发当前组件以及它所在组件树的所有祖先和后代组件的变化检测,不在一个分支上的组件不会检测,比如我的组件使用OnPush模式,组件模板中有一个按钮,按钮的事件处理修改组件的数据,这个事件可以直接触发组件的变化检测,无需单独调用检测,并且这个检测会在当前组件的所有链条上传递即使组件是OnPush模式。

这个 同步事件 包括点击事件、ngModel值的更新等

问题

当组件使用OnPush模式时,如果我在组件的事件处理中修改一个变量,而这个变量需要通过NgModel传递给一个子组件,这个时候不会触发子组件的变化检测,也就是我传递一个值给NgModel不会显示到界面,这个问题也有人给Angular提了Issue,原因应该就是如下代码,更改ngModel值的过程被放到了一个异步处理,在执行的时候事件触发的变化检测已经完成,因为OnPush的原因该组件及子组件又不会重新触发变化检测,所以ngModel的值不会及时更新模板

private _updateValue(value: any): void {resolvedPromise.then(() => { this.control.setValue(value, {emitViewToModelChange: false}); });}

手动操作变化检测

constructor(private changeDectorRef:ChangeDetectorRef
){}

  • markForCheck() - 在组件的 metadata 中如果设置了 changeDetection:ChangeDetectionStrategy.OnPush 条件,那么变化检测不会再次执行,除非手动调用该方法, 该方法的意思是在变化监测时必须检测该组件。
  • detectChanges() - 从该组件到各个子组件执行一次变化检测

这块的理解很大一部分是老大的指点,鸣谢 @徐海峰

vb.net变量值变化触发事件_Angular变化检测的理解相关推荐

  1. keil5中如何实时查看变量值

    在调试程序中经常需要观察变量的值,那么在keil中如何查看变量值. 首先进入仿真界面 比如要观察局部变量i.j.k的值,首先将变量选中,然后右键选择 Add "i" to Watc ...

  2. angular监听输入框值的变化_angular 实时监听input框value值的变化触发函数方法

    用angulajs + ionic 做了一个登陆页面.效果要通过监听输入框的变化来判断登陆按钮是否可点击.当至少一个输入框为空时登录按钮不可点击.一开始是用的jquery的方法做的,后来发现刷新当前页 ...

  3. pythontk界面显示函数中的变量值_简单易学,西门子触摸屏3种修改变量值的方法!博图Wincc V14组态...

    应条友要求,今天分享3种修改触摸屏变量值的最常用方法! 全文约700字,通读4分钟! 看完本章,你将收获以下内容: 一:必会知识点:3种修改变量的方法及适用点 二:实例:3种方法修改触摸屏变量值 三: ...

  4. keil debug如何在watch直接修改变量值_零基础学VBA:什么是VBA?如何编写和运行VBA代码?...

    HI,大家好,我是星光,今天咱们来继续学习VBA.在上一章咱们讲了为什么要学习VBA~VBA还值不值得学~学了还有没有用~零基础学VBA编程01:VBA还能不能学?学了还有没有用? 这一章咱们再来简单 ...

  5. 《基于Qt的VR编辑器开发》(Yanlz+Unity+SteamVR+5G+AI+VR云游戏+Qt+编辑器+跨平台+人机交互+触发事件+立钻哥哥+==)

    <基于Qt的VR编辑器开发> <基于Qt的VR编辑器开发> 版本 作者 参与者 完成日期 备注 YanlzFramework_Qt_V01_1.0 严立钻 2019.09.04 ...

  6. 在C#中使用代理的方式触发事件

    事件(event)是一个非常重要的概念,我们的程序时刻都在触发和接收着各种事件:鼠标点击事件,键盘事件,以及处理操作系统的各种事件.所谓事件就是由某个对象发出的消息.比如用户按下了某个按钮,某个文件发 ...

  7. 在C#中使用代理的方式触发事件 (委托和事件 ) (转)

    From:  http://www.cnblogs.com/gzhnan/articles/1859477.html 在C#中使用代理的方式触发事件 (委托和事件 ) 事件(event)是一个非常重要 ...

  8. jquery的实时触发事件(textarea实时获取中文个数)

    jquery的实时触发事件(textarea实时获取中文个数) (2014-09-16 11:49:50) 转载▼ 标签: 实时触发事件 中文个数 onpropertychange oninput o ...

  9. js 获取表格数据(表单变量值)

    js获取表单中的指定动态变量 问题描述:for循环实现表格每行数据输入,对应每行有提交表单需要做相应处理,我们需要获得该行某列的变量值 要求:表格每一行有一个提交按钮实现前台判断操作(判断表格每行第二 ...

最新文章

  1. Java业务代表模式
  2. iPhone曝严重漏洞,用户接听FaceTime前或被“监听”!
  3. @select 怎么写存储过程_MySQL4:存储过程和函数
  4. 201312-2_ISBN号码
  5. msyql开启慢查询以及分析慢查询
  6. js数组去重方法分析与总结
  7. Aplication的意义和生命周期,与Context的关系,以及关于Aplication和Context相关问题的记录和解决办法...
  8. java怎么递归_什么是递归?用Java写一个简单的递归程序
  9. 【3389】俄远程桌面多端口爆破
  10. Python判断素数
  11. PAT B 1068 万绿丛中一点红(C语言)*排除法
  12. poc测试环境准备_POC测试经验总结
  13. ORACLE FORMS BUILDER的布局和常用ITEMS
  14. 联想电脑ctrl + r 快捷键无法使用
  15. 【问题记录】ABP框架模板页面样式加载不完全
  16. 加解密,加签、验签也就这肥事
  17. wps 分节符(连续) 自动变成 分节符(下一页) 解决办法
  18. 百度产品战略的变化历程
  19. 对自动变速器的控制器建模
  20. 生命有一种负重叫时间

热门文章

  1. 攻防世界web新手区解题 view_source / robots / backup
  2. php井字游戏代码_PHP初级笔试题:Tic-Tac-Toe(n阶井字棋)判断胜负
  3. php 导出excel 特殊字符,PHPEXCEL导出,存在特殊字符遇到的问题
  4. html中.inner样式,JavaScript-DOM动态控制Html标签对象样式和innerHTML、className属性
  5. python 命名空间冲突_python-命名空间
  6. Python 面向对象 实例方法 属性 (上)
  7. MySQL:基本命令
  8. 洛谷P2016 战略游戏【树形dp】
  9. 127.0.0.1与localhost的区别
  10. 饶军:Apache Kafka的过去,现在,和未来