Vue2源码解读 - 响应式原理及简单实现
直接进入主题了,想必大家都知道实现vue响应式核心方法就是 Object.defineProperty
,那就从它开始说
Object.defineProperty
缺点:
- 深度监听,需要递归到底,一次性计算量大
- 无法监听新增、删除属性(需要vue.set 和 vue.delete)
- 无法原生监听数组,需要特殊处理
实现响应式
function updateView () {
console.log('视图更新')
}
// 重新定义数组原型
const oldArrayProperty = Array.prototype
// 创建新对象原型指向 Array.prototype,在扩展新的方法不会影响原型
const arrProto = Object.create(oldArrayProperty);
['push', 'pop', 'shift', 'unshift', 'splice'].forEach(methodName => {
arrProto[methodName] = function () {
updateView()
oldArrayProperty[methodName].call(this, ...arguments)
}
});
// 监听data传入的属性
function defineReactive(target, key, value) {
// 深度监听 多层对象嵌套
observer(value)
// 核心api
Object.defineProperty(target, key, {
get() {
return value
},
set(newVal) {
// 设置新值也要监听 比如{age:27}
observer(newVal)
if (newVal !== value ) {
value = newVal
updateView()
}
}
})
}
// 监听对象属性
function observer(target) {
if (typeof target !== 'object' || target === null) {
// 不是对象或数组
return target
}
// 监听数组 把原数组的隐式原型赋值给我们定义好的数组对象
if (Array.isArray(target)) {
target.__proto__ = arrProto
}
// 重新定义各个属性,加getter、setter属性
for(let key in target) {
defineReactive(target, key, target[key])
}
}
const data = {
name: 'zk',
age: 26,
info: {
address: 'city' // 需深度监听
},
nums: [1, 2, 3]
}
observer(data)
// data.info.address = 'beijing' // 需要深度监听
// data.info = {address:'beijing'} // 需要深度监听
// data.x = 666 // 新增属性,监听不到 需要vue.set方法
// delete data.name // 删除属性,监听不到 需要vue.delete方法
data.nums.push(21)
vue2简单的数据双向绑定实现
<div>内容:<span id="content"></span></div>
<input id="iptName" />
const iptName = document.getElementById('iptName')
const content = document.getElementById('content')
let obj = {
name: ''
}
let newObj = JSON.parse(JSON.stringify(obj))
Object.defineProperty(obj, 'name', {
get() {
return newObj.name
},
set(val) {
if (val === newObj.name) return
newObj.name = val
observer()
}
})
function observer () {
iptName.innerText = obj.name
content.innerText = obj.name
}
iptName.oninput = function () {
obj.name = this.value
}
Vue2源码解读 - 响应式原理及简单实现的更多相关文章
- vue源码之响应式数据
分析vue是如何实现数据响应的. 前记 现在回顾一下看数据响应的原因. 之前看了vuex和vue-i18n的源码, 他们都有自己内部的vm, 也就是vue实例. 使用的都是vue的响应式数据特性及$w ...
- Spring:源码解读Spring IOC原理
Spring IOC设计原理解析:本文乃学习整理参考而来 一. 什么是Ioc/DI? 二. Spring IOC体系结构 (1) BeanFactory (2) BeanDefinition 三. I ...
- Spring源码解读Spring IOC原理
一.什么是Ioc/DI? IoC 容器:最主要是完成了完成对象的创建和依赖的管理注入等等. 先从我们自己设计这样一个视角来考虑: 所谓控制反转,就是把原先我们代码里面需要实现的对象创建.依赖的代码,反 ...
- 通用后台管理系统源码,响应式布局,Java管理系统源码,零门槛安装部署
本项目是一个通用响应式管理后台,导入开发环境安装就能直接运行,界面也非诚漂亮,在PC端和移动端也是自适应的.非常适合企业或者个人搭建各种商城后台,博客后台,网站管理后台等. 源码启动后的截图 需要这套 ...
- Python Web Flask源码解读(二)——路由原理
关于我 一个有思想的程序猿,终身学习实践者,目前在一个创业团队任team lead,技术栈涉及Android.Python.Java和Go,这个也是我们团队的主要技术栈. Github:https:/ ...
- JGUI源码:响应式布局简单实现(13)
首先自我检讨下,一直没有认真研究过响应式布局,有个大致概念响应式就是屏幕缩小了就自动换行或者隐藏显示,就先按自己的理解来闭门造车思考实现过程吧. 1.首先把显示区域分成12等分,bootstrap是这 ...
- java 企业门户网站 源码 自适应响应式 freemarker 静态引擎 html5 SSM
官网 http://www.fhadmin.org/ 系统介绍: 1.网站后台采用主流的 SSM 框架 jsp JSTL,网站后台采用freemaker静态化模版引擎生成html 2.因为是生成的ht ...
- vue2.0 之 深入响应式原理
实例demo<div id="app"> <span>{{a}}</span> <input type="text" ...
- 2,MapReduce原理及源码解读
MapReduce原理及源码解读 目录 MapReduce原理及源码解读 一.分片 灵魂拷问:为什么要分片? 1.1 对谁分片 1.2 长度是否为0 1.3 是否可以分片 1.4 分片的大小 1.5 ...
随机推荐
- NOIP模拟38:b
这是T2. 一个容斥(其实也可以欧拉反演做,但是我不会). 首先开一个桶,记录第i行的j有多少个. 然后枚举1-\(maxn\),枚举他的值域内的倍数,记录倍数在第i行有多少个,将个数 ...
- Spring Dependency Injection浅析
Dependency Injection 依赖注入,在Spring框架负责创建Bean对象时,动态的将依赖对象注入到Bean组件. 1.在UserService中提供一个get/set的name方法, ...
- 查询同一张表符合条件的某些数据的id拼接成一个字段返回
同一张表存在类似多级菜单的上下级关系的数据,查询出符合条件的某些数据的id拼接成一个字段返回: SELECT CONCAT(a.pid, ',', b.subid) AS studentIDS FRO ...
- 【第六篇】- Maven 仓库之Spring Cloud直播商城 b2b2c电子商务技术总结
Maven 仓库 在 Maven 的术语中,仓库是一个位置(place). Maven 仓库是项目中依赖的第三方库,这个库所在的位置叫做仓库. 在 Maven 中,任何一个依赖.插件或者项目构建的输出 ...
- freeswitch 编译安装后的配置
--------------------FreeSWITCH configuration------------Locations: prefix: /usr/local/freeswitchexec ...
- electron-vue 开发问题合集
(一)Found 'electron' but not as a devDependency, pruning anyway 原因:对electron没有严格要求的话可以忽略,不影响打包,但会影响第三 ...
- 使用 elementUI 树形控件Tree 编辑数据
操作新增/编辑功能时初始化数据: 应用属性 default-checked-keys 给Tree节点赋默认值(赋值数据为节点数组Arr)前,应先清空数组Arr,并且配合使用 this.$refs.tr ...
- STM32F103C8T6使用SPI接口驱动WS2812b灯条
之前一篇文章写了使用IO控制WS2812b操作原理,但是由于IO的输出比较慢,所以现在改用了硬件SPI控制WS2812b灯条 把SPI的mosi线接到ws2812b的数据线,SPI的速率可达十几Mbi ...
- pandas学习小记
pandas操作整理 导入数据: pd.read_csv(filename):从CSV文件导入数据 pd.read_table(filename):从限定分隔符的文本文件导入数据 pd.read_ex ...
- 『GoLang』反射
方法和类型的反射 反射是应用程序检查其所拥有的结构,尤其是类型的一种能.每种语言的反射模型都不同,并且有些语言根本不支持反射.Go语言实现了反射,反射机制就是在运行时动态调用对象的方法和属性,即可从运 ...