vue无法检测数组变动的原因

6 篇文章 0 订阅
3 篇文章 0 订阅

前言

在vue 2.x版本中,vue无法对数组的增加、删除等操作进行检测并派发视图更新。同理,对于已创建对象实例的属性增加、删除操作也会无法达到监听的目的,虽然对于诸如此类问题都有如$set、数组重构、主动通知vue更新等相应的解决办法。但是对于其产生原理,则需要从vue的响应式实现方式谈起。

响应式原理

在vue 2.x版本中,针对每一个对象的属性,都是采用的Object.defineProperty()方法,对已创建的对象实例中的每一个属性添加getter/setter方法以拦截该对象每一次的数据变动。通俗地讲,可以认为这种做法等同于对每一次数据变动添加了一层拦截器/陷阱函数,而后在每一次的枚举中,通过getter函数中收集更新依赖并添加至订阅者Dep对象,再通过setter函数触发依赖通知观察者watcher更新视图,vue也正是通过该原理实现的动态响应。

为何限制

在了解了vue的响应式原理后,不难看出,其实vue是可以针对数组的变动进行检测而触发响应式更新视图。那么为什么vue的开发者没有这么做?在vue的官方文档中对该问题的阐述为JavaScript限制,那么在阅读完上文后能够知晓其实JavaScript并没有对这类操作存在限制,那么这个限制到底是什么?

产生原因

真正限制vue无法对数组进行动态响应的根本原因,来源于JavaScript对数组操作的限制。对于对象而言,每一次的数据变更都会对对象的属性进行一次枚举,一般对象本身的属性数量有限,所以对于遍历枚举等方式产生的性能损耗可以忽略不计,但是对于数组而言呢?数组包含的元素量是可能达到成千上万,假设对于每一次数组元素的更新都触发了枚举/遍历,其带来的性能损耗将与获得的用户体验不成正比,故vue无法检测数组的变动。

未来?

在未来发布的vue3.0中,将使用proxy代理模式替代Object.defineProperty(),其在代码层面将更加简洁,执行效率也大幅提升,数据检测也由属性转变为对象,不过由于其兼容性导致使用广度并未充分扩散。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值