对Angular中单向数据流的深入理解


Posted in Javascript onMarch 31, 2018

变更检测

Angular 中,数据是由顶部根节点流向最后的叶子节点,整个数据流是单向,构成一颗单向树。

对Angular中单向数据流的深入理解

Angular 认为所有的异步操作都有可能会引起模型的变化,引起数据模型发生变化的事件源有:

  • Events:click, mouseover, keyup ...
  • Timers:setInterval、setTimeout
  • XHRs:Ajax(GET、POST ...)

Angular 封装 Zone来拦截跟踪异步,一旦发现异步行为,Angular 就会进行变更检测。

因为数据流是单向的,组件的数据来源只能由父组件进行传入,所以 Angular 会从上到下,广度遍历检测组件,只要父组件检测完毕就能继续检测子组件。而相比 angularjs,双向、混乱的数据流方向,会导致重复变更检测重复多次,直到数据稳定,可能会导致性能问题,或者出现数据和视图处于不一致的状态,即渲染过程完成后的视图不能反映数据的实际状态。

渲染输出

当检测到数据模型变化时,组件需要重新渲染,Angular将运行它的 DOM 生成函数,该函数会生成一个新的 DOM数据结构,该结构对应于组件 View 的新版本。

Angular 在渲染过程中,评估模板表达式并在整个组件树中调用生命周期钩子。

注意:绿色标志会多次调用

对Angular中单向数据流的深入理解

从生命调用周期来看(绿色有向线),ngAfterViewChecked 标示该组件及子组件视图输出完成。看以下一例子:

import {Component, AfterViewChecked} from '@angular/core';
import {Course} from "./course";
@Component({
 selector: 'app-root',
 template: `
 <div class="course">
  <span class="description">{{course.description}}</span>
 </div>
`})
export class AppComponent implements AfterViewChecked {
 course: Course = {
  id: 1,
  description: "Angular For Beginners"
 };

 ngAfterViewChecked() {
  this.course.description += Math.random();
 }
}

上述代码会在Angular变更检测周期发生错误。组件已经完成 DOM 数据结构输出,我们还在该组件 ngAfterViewChecked() 方法中修改了数据状态。这样导致了视图渲染后,数据跟视图状态不一致。

数据从组件类流向表示它们的DOM数据结构,生成这些DOM数据结构的行为本身就不会导致数据的进一步修改。但我们在 ngAfterView 生命周期发生修改数据行为,Angular 的“单向数据流”规则禁止在一个视图已经被组合好之后再更新视图。
这意味着数据模型到视图过程是单向,不可在视图后发生数据流发生改变。

总结

从变更检测过程以及渲染输出过程中,可以总结出:

单向数据流指的是从组件树的顶部到底部渲染扫描过程中应用程序数据流转到由渲染过程生成的输出DOM数据结构的流程。

好了,以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,如果有疑问大家可以留言交流,谢谢大家对三水点靠木的支持。

Javascript 相关文章推荐
js每次Title显示不同的名言
Sep 25 Javascript
使用Jquery Aajx访问WCF服务(GET、POST、PUT、DELETE)
Mar 16 Javascript
jQuery实现带滚动线条导航效果的方法
Jan 30 Javascript
Js数组排序函数sort()介绍
Jun 08 Javascript
javascript实现类似java中getClass()得到对象类名的方法
Jul 27 Javascript
用jQuery获取table中行id和td值的实现代码
May 19 Javascript
Vue中的混入的使用(vue mixins)
Jun 01 Javascript
浅谈vue首屏加载优化
Jun 28 Javascript
vue中使用input[type=&quot;file&quot;]实现文件上传功能
Sep 10 Javascript
vue项目中仿element-ui弹框效果的实例代码
Apr 22 Javascript
JS算法教程之字符串去重与字符串反转
Dec 15 Javascript
如何封装Vue Element的table表格组件
Feb 06 Vue.js
jQuery中复合选择器简单用法示例
Mar 31 #jQuery
jQuery中内容过滤器简单用法示例
Mar 31 #jQuery
jQuery中可见性过滤器简单用法示例
Mar 31 #jQuery
Postman模拟发送带token的请求方法
Mar 31 #Javascript
浅谈Postman解决token传参的问题
Mar 31 #Javascript
postman+json+springmvc测试批量添加实例
Mar 31 #Javascript
JS和Canvas实现图片的预览压缩和上传功能
Mar 30 #Javascript
You might like
追求程序速度,而不是编程的速度
2008/04/23 PHP
php radio 单选框获取与保持值的实现代码
2010/05/15 PHP
深入PHP与浏览器缓存的分析
2013/06/03 PHP
php获取随机数组列表的方法
2014/11/13 PHP
win7安装php框架Yii的方法
2016/01/25 PHP
PHP中的print_r 与 var_dump 输出数组
2016/06/13 PHP
PHP操作MySQL中BLOB字段的方法示例【存储文本与图片】
2017/09/15 PHP
通过jQuery打造支持汉字,拼音,英文快速定位查询的超级select插件
2010/06/18 Javascript
关于ExtJS4.1:快捷键支持的问题
2013/04/24 Javascript
上传的js验证(图片/文件的扩展名)
2013/04/25 Javascript
JavaScript动态插入script的基本思路及实现函数
2013/11/11 Javascript
单击和双击事件的冲突处理示例代码
2014/04/03 Javascript
JavaScript基础教程——入门必看篇
2016/05/20 Javascript
JQuery ZTree使用方法详解
2017/01/07 Javascript
Node.js调用fs.renameSync报错(Error: EXDEV, cross-device link not permitted)
2017/12/27 Javascript
用node.js写一个jenkins发版脚本
2019/05/21 Javascript
Vue为什么要谨慎使用$attrs与$listeners
2020/08/27 Javascript
vue实现简易计算器功能
2021/01/20 Vue.js
跟老齐学Python之再深点,更懂list
2014/09/20 Python
python实现的AES双向对称加密解密与用法分析
2017/05/02 Python
matplotlib作图添加表格实例代码
2018/01/23 Python
Python+Selenium+phantomjs实现网页模拟登录和截图功能(windows环境)
2019/12/11 Python
HTML5 WebGL 实现民航客机飞行监控系统
2019/07/25 HTML / CSS
CAT鞋加拿大官网:CAT Footwear加拿大
2020/08/05 全球购物
外贸业务员求职信范文
2013/12/12 职场文书
金融行业务员的自我评价
2013/12/13 职场文书
阳光体育活动方案
2014/02/16 职场文书
小学生新年寄语
2014/04/03 职场文书
班风口号
2014/06/18 职场文书
中职生求职信
2014/07/01 职场文书
主题党日活动总结
2014/07/08 职场文书
2014年安全生产责任书
2014/07/22 职场文书
同事去世追悼词
2015/06/23 职场文书
2019年特色火锅店的创业计划书模板
2019/08/28 职场文书
Node-Red实现MySQL数据库连接的方法
2021/08/07 MySQL
HTML中的表单元素介绍
2022/02/28 HTML / CSS