谈谈对vue响应式数据更新的误解


Posted in Javascript onAugust 01, 2017

对于刚接触vue的同学会经常遇到数据更新了但是模板没有更新的问题,下面将结合vue的响应式特性以及异步更新机制分析常见的错误:

异步更新带来的数据响应式误解

异步数据的处理基本是一定会遇到的,处理不好就会遇到数据不更新的问题,但有一种情况是在未正确处理的情况下也能正常更新,这就会造成一种误解,详情如下所示:

模板

<div id="app">
    <h2>{{dataObj.text}}</h2>
</div>

js

new Vue({
      el: '#app',
      data: {
        dataObj: {}
      },
      ready: function () {
        var self = this;

        /**
         * 异步请求模拟
         */
        setTimeout(function () {
          self.dataObj = {}; 
          self.dataObj['text'] = 'new text';
        }, 3000);
      }
    })

上面的代码非常简单,我们都知道vue中在data里面声明的数据才具有响应式的特性,所以我们一开始在data中声明了一个dataObj空对象,然后在异步请求中执行了两行代码,如下:

self.dataObj = {}; 
self.dataObj['text'] = 'new text';

首先清空原始数据,然后添加一个text属性并赋值。到这里为止一切都如我们所想的,数据和模板都更新了。

那么问题来了,dataObj.text具有响应式的特性吗?

模板更新了,应该具有响应式特性,如果这么想那么你就已经走入了误区,一开始我们并没有在data中声明.text属性,所以该属性是不具有响应式的特性的。

但模板切切实实已经更新了,这又是怎么回事呢?

那是因为vue的dom更新是异步的,即当setter操作发生后,指令并不会立马更新,指令的更新操作会有一个延迟,当指令更新真正执行的时候,此时.text属性已经赋值,所以指令更新模板时得到的是新值。

具体流程如下所示:

  1. self.dataObj = {};发生setter操作
  2. vue监测到setter操作,通知相关指令执行更新操作
  3. self.dataObj['text'] = 'new text';赋值语句
  4. 指令更新开始执行

所以真正的触发更新操作是self.dataObj = {};这一句引起的,所以单看上述例子,具有响应式特性的数据只有dataObj这一层,它的子属性是不具备的。

对比示例:

模板

<div id="app">
    <h2>{{dataObj&&dataObj.text}}</h2>
</div>

js

new Vue({
      el: '#app',
      data: {
        dataObj: {}
      },
      ready: function () {
        var self = this;

        /**
         * 异步请求模拟
         */
        setTimeout(function () {
          self.dataObj['text'] = 'new text';
        }, 3000);
      }
    })

上述例子的模板是不会更新的。

Vue.$set

通过$set方法可以将添加一个具备响应式特性的属性,并且其子属性也具备响应式特性,但是必须是新属性才可以,如果是本身已有的属性该方法是不起作用的。

new Vue({
      el: '#app',
      data: {
        dataObj: {}
      },
      ready: function () {
        var self = this;

        /**
         * 异步请求模拟
         */
        setTimeout(function () {
          var data = {
            name: 'xiaofu',
            age: 18
          };
          var data01 = {
            name: 'yangxiaofu',
            age: 19
          };
          self.dataObj['person'] = {};
          self.$set('dataObj.info', data);
          self.$set('dataObj.person', data01); 
        }, 3000);
      }
    })

如上所示, .person属性是不具备响应式特性的。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
javascript学习笔记(十九) 节点的操作实现代码
Jun 20 Javascript
Extjs显示从数据库取出时间转换JSON后的出现问题
Nov 20 Javascript
js图片延迟加载的实现方法及思路
Jul 22 Javascript
js插件设置innerHTML时在IE8下提示“未知运行时错误”解决方法
Apr 25 Javascript
JavaScript提高网站性能优化的建议(二)
Jul 24 Javascript
javascript鼠标滑过显示二级菜单特效
Nov 18 Javascript
JavaScript 实现的checkbox经典实例分享
Oct 16 Javascript
jQuery 检查某个元素在页面上是否存在实例代码
Oct 27 Javascript
浅谈javascript中执行环境(作用域)与作用域链
Dec 08 Javascript
JS使用ActiveXObject实现用户提交表单时屏蔽敏感词功能
Jun 20 Javascript
JavaScript实现简单的双色球(实例讲解)
Jul 31 Javascript
jQuery实现当拉动滚动条到底部加载数据的方法分析
Jan 24 jQuery
详解jquery选择器的原理
Aug 01 #jQuery
浅谈node中的exports与module.exports的关系
Aug 01 #Javascript
Vue2.0 组件传值通讯的示例代码
Aug 01 #Javascript
谈谈VUE种methods watch和compute的区别和联系
Aug 01 #Javascript
Angular4学习笔记之实现绑定和分包
Aug 01 #Javascript
详解js静态资源文件请求的处理
Aug 01 #Javascript
Angular4学习笔记之准备和环境搭建项目
Aug 01 #Javascript
You might like
2019十大人气国漫
2020/03/13 国漫
全文搜索和替换
2006/10/09 PHP
一道求$b相对于$a的相对路径的php代码
2010/08/08 PHP
PHP生成随机密码类分享
2014/06/25 PHP
PHP中使用localhost连接Mysql不成功的解决方法
2014/08/20 PHP
php自定义apk安装包实例
2014/10/20 PHP
PHP实现多关键字加亮功能
2016/10/21 PHP
jquery插件jTimer(jquery定时器)使用方法
2013/12/23 Javascript
jquery用data方法获取某个元素上的事件
2014/06/23 Javascript
简介AngularJS的视图功能应用
2015/06/17 Javascript
jQuery插件实现文件上传功能(支持拖拽)
2020/08/27 Javascript
window.open打开窗口被拦截的快速解决方法
2016/08/04 Javascript
微信小程序 实现tabs选项卡效果实例代码
2016/10/31 Javascript
Vue数据驱动模拟实现5
2017/01/13 Javascript
Angular.Js之Scope作用域的学习教程
2017/04/27 Javascript
通过vue提供的keep-alive减少对服务器的请求次数
2018/04/01 Javascript
angularjs通过过滤器返回超链接的方法
2018/10/26 Javascript
图文讲解vue的v-if使用方法
2019/02/11 Javascript
JavaScript页面加载事件实例讲解
2019/09/01 Javascript
浅析webpack-bundle-analyzer在vue-cli3中的使用
2019/10/23 Javascript
vuejs element table 表格添加行,修改,单独删除行,批量删除行操作
2020/07/18 Javascript
[47:31]完美世界DOTA2联赛PWL S3 INK ICE vs DLG 第一场 12.12
2020/12/16 DOTA
Python中的pprint折腾记
2015/01/21 Python
用virtualenv建立多个Python独立虚拟开发环境
2017/07/06 Python
解决PyCharm的Python.exe已经停止工作的问题
2018/11/29 Python
Python 经典算法100及解析(小结)
2019/09/13 Python
Python小白学习爬虫常用请求报头
2020/06/03 Python
H5 meta小结(前端必看篇)
2016/08/24 HTML / CSS
Burberry英国官网:英国标志性奢侈品牌
2017/03/29 全球购物
对于没有初始化的变量的初始值可以作怎样的假定
2014/10/12 面试题
养生餐厅创业计划书范文
2014/03/26 职场文书
学校宣传标语
2014/06/18 职场文书
铣工实训报告
2014/11/05 职场文书
扬州个园导游词
2015/02/06 职场文书
中学教代会开幕词
2016/03/04 职场文书
五年级作文之成长
2019/09/16 职场文书