第9集丨Vue 江湖 —— 监测数据原理

news2024/12/23 6:38:37

目录

  • 一、修改数据时的一个问题
    • 1.1 现象一
    • 1.2 现象二
  • 二、Vue监测数据原理
    • 2.1 模拟一个数据监测
    • 2.2 数据劫持
    • 2.3 Vue.set()/vm.$set()
    • 2.4 基本原理
      • 2.4.1 如何监测对象中的数据?
      • 2.4.2 如何监测数组中的数据?
      • 2.4.3 修改数组中的某个元素
    • 2.5 案例
      • 2.5.1 需求功能
      • 2.5.2 实现

一、修改数据时的一个问题

下面案例中,我们定义了一个按钮,期望是:点击按钮更新persons[0] 的信息。

但实际问题是:Vue监测不到数据的变化。

<div id="root">
    <h2>列表过滤</h2>
    <button @click="change">更新令狐冲信息</button>
    <ul>
        <li v-for="(p,index) in persons" :key="p.id" >
            {{p.name}} - {{p.use}} - {{p.age}}
        </li>
    </ul>
    
</div>
<script>
    const vm = new Vue({
        el:'#root',
        data:{
            persons:[
                {id:'001',name:'令狐冲',use:"独孤九剑",sex:'男',age:20},
                {id:'002',name:'任盈盈',use:"仙女下凡",sex:'女',age:19},
                {id:'003',name:'任我行',use:"吸星大法",sex:'男',age:50}
            ]
        },
        methods: {
            change(){
                // 可行的方式
                // this.persons[0].name = "假的令狐冲";
                // this.persons[0].use = "葵花宝典";
                // this.persons[0].age = 100;

                // Vue没发现你修改了数据,其实已经改了
                this.persons[0] = {id:'001',name:'假的令狐冲',use:"葵花宝典",sex:'男',age:100}
                
            }
        },
    })
</script>

1.1 现象一

  1. 在浏览器中打开页面,在打开vue-devtools
  2. 点击按钮
  3. 观察工具中的数据,竟然没有发生变化!!!但其实数据已经真实改变了
  4. 我们可以通过控制台,输入vm.persons[0] 查看,发现数据确实变了。

在这里插入图片描述

1.2 现象二

  1. 在浏览器中打开页面,然后先点击按钮
  2. 再打开vue-devtools
  3. 查看工具中数据,发现数据改变了!!!

在这里插入图片描述

二、Vue监测数据原理

2.1 模拟一个数据监测

下面案例中,当data的数据发生变化,就会在控制台打印出一句话。

let data = {
    name:'令狐冲',
    menpai:'华山派'
}

// 创建一个监视的实例对象,用于监视data中属性的变化
const obs = new Observer(data)

// 准备一个vm的实例对象
let vm = {}
vm._data = data = obs;

function Observer (obj) {
    // 汇总对象中所有的属性形成一个数组
    const keys = Object.keys(obj);
    
    keys.forEach((k)=>{
        Object.defineProperty(this,k,{
            get(){
                return obj[k]
            },
            set(val){
                console.log(`${k}被改了,之后解析模板,生成虚拟DOM....`);
                obj[k] = val
            }
        })
    })
}

2.2 数据劫持

数据劫持:在访问或修改对象的某个属性时,通过一段代码拦截这个行为,进行额外的操作,如修改返回结果。

Vue 2.x 使用的是 Object.defineProperty(),而 Vue3.x 版本之后改用 Proxy 进行实现

2.3 Vue.set()/vm.$set()

  • 语法:Vue.set( target, propertyName/index, value )

  • 功能:向响应式对象中添加一个 property,并确保这个新property同样是响应式的,且触发视图更新

  • 注意:它必须用于向响应式对象上添加新 property,因为 Vue无法探测普通的新增 property (比如 this.myObject.newProperty = 'hi')

 Vue.set(this.person.hobby, 0, "哈哈哈")
 this.$set(this.person.hobby, 0, "哈哈哈")
 // 从第0个位置,删一个,在插入一个
// this.person.hobby.splice(0,1,"哈哈哈")

2.4 基本原理

Vue监测到data中的数据(所有层次的数据)发生变化,就会调用setter重新解析模板,解析引用的到的数据的值。

2.4.1 如何监测对象中的数据?

  • 通过setter实现监视,且要在new Vue时就传入要监测的数据。

    (1). 对象中后追加的属性,Vue默认不做响应式处理
    (2). 如需给后添加的属性做响应式,请使用如下API:

      Vue.set(target, propertyName/index,value)
      vm.$set(target, propertyName/index,value)
    

2.4.2 如何监测数组中的数据?

Vue通过包裹数组的更新元素的方法实现,本质就是做了两件事:

  • (1). 调用原生对应的方法对数组进行更新。
  • (2). 重新解析模板,进而更新页面。

数组中这些被包裹过的方法包括:

  • push()
  • pop()
  • shift()
  • unshift()
  • splice()
  • sort()
  • reverse()

2.4.3 修改数组中的某个元素

Vue中,修改数组中的某个元素一定要用如下方法,才能实现响应式:

  • 被包裹过的方法:push()、pop()、shift()、unshift()、splice()、sort(). reverse()
  • 通过Vue.set()vm.$set()

注意Vue.set()vm.$set() 不能给vmvm的根数据对象(vm.data)添加属性。

2.5 案例

2.5.1 需求功能

  • 需求如下截图

在这里插入图片描述

2.5.2 实现

<div id="root">
    <h2>笑傲江湖</h2>
    <hr>
    <div>
        <button @click="person.age++">年龄+1岁</button> 
        <button @click="addSex">添加性别属性,默认值:男</button> 
        <button @click="addFriend">在列表首位添加一个朋友</button>
        <button @click="updateFName">修改第一个朋友的名字为:小三</button>
        <button @click="addHobby">添加一个爱好</button>
        <button @click="updateHobby">修改第一个爱好为: 哈哈哈</button>
        <button @click="removeHobby">过滤爱好中的喝酒</button>
    </div>
    <h3>姓名:{{person.name}}</h3>
    <h3>年龄:{{person.age}}</h3>
    <h3 v-if="person.sex">性别:{{person.sex}}</h3>
    <h3>爱好:</h3>
    <ul>
        <li v-for="(h,index) in person.hobby" ::key="index">
            {{h}}
        </li>
    </ul>

    <h3>朋友:</h3>
    <ul>
        <li v-for="(f,index) in person.friends" ::key="index">
            {{f.name}} - {{f.age}}
        </li>
    </ul>

</div>
<script>
    const vm = new Vue({
        el:'#root',
        data:{
            person:{
                name:'令狐冲',
                age:26,
                hobby:['喝酒','练剑','行侠仗义'],
                friends:[
                    {name:'田伯光',age:30},
                    {name:'任我行',age:50}
                ]
            }
        },
        methods: {
            addSex(){
                // Vue.set(this.person,'sex','男')
                this.$set(this.person,'sex','男')
            },
            addFriend(){
                this.person.friends.unshift({name:'任盈盈',age:'26'})
            },
            updateFName(){
                this.person.friends[0].name = '小三'
            },
            addHobby(){
                this.person.hobby.push('大笑')
            },
            updateHobby(){
                // 从第0个位置,删一个,在插入一个
                // this.person.hobby.splice(0,1,"哈哈哈")
                // Vue.set(this.person.hobby, 0, "哈哈哈")
                this.$set(this.person.hobby, 0, "哈哈哈")
            },
            removeHobby(){
                this.person.hobby = this.person.hobby.filter((h)=>{
                    return h !== "喝酒"
                })
            }
        },
    })
</script>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/857657.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【深度学习 video detect】Towards High Performance Video Object Detection for Mobiles

文章目录 摘要IntroductionRevisiting Video Object Detection BaselinePractice for Mobiles Model Architecture for MobilesLight Flow 摘要 尽管在桌面GPU上取得了视频目标检测的最近成功&#xff0c;但其架构对于移动设备来说仍然过于沉重。目前尚不清楚在非常有限的计算…

android studio 实用插件推荐

本文字数&#xff1a;&#xff1a;2352字 预计阅读时间&#xff1a;8分钟 背景 现在做安卓开发的同学基本都是用 Android Studio 了吧&#xff0c;它具有强大的开放性&#xff0c;可以让用户根据自己的需求开发或使用一些插件辅助自己搬砖&#xff0c;当然开发插件我们可能还没…

操作系统—调度算法

进程调度算法 进程调度算法也称CPU调度算法 调度发生时期 当进程从运行状态转到等待状态&#xff1b;当进程从运行状态转到就绪状态&#xff1b;当进程从等待状态转到就绪状态&#xff1b;当进程从运行状态转到终止状态&#xff1b; 其中发生在 1 和 4 两种情况下的调度称为…

工业无线技术应用-无线控制斗轮机启停、故障等开关信号

斗轮堆取料机是一种对散料进行连续堆取作业的高效装卸大型机械,被广泛使用于火力发电厂和炼焦厂的输煤系统中。目前对斗轮机的技改主要为将斗轮机的部分程控信号改为无线传输&#xff0c;取代卷筒电机和电缆的应用。 多数情况下都是利用无线通讯做媒介&#xff0c;让工作人员通…

Shopee买家通系统可全自动批量注册虾皮买家号

Shopee买家通系统可批量注册虾皮买家号&#xff0c;如果想要拥有大量虾皮买家号&#xff0c;完全可以试试&#xff0c; 不过在注册之前我们需要先准备好账号所需要的资料&#xff0c;比如邮箱、手机号、ip、收货地址等。不过想要账号能自动化&#xff0c;对于账号资料也是有一…

SSL证书DV和OV的区别?

SSL证书是在互联网通信中保护数据传输安全的一种加密工具。它能够确保客户端和服务器之间的通信得以加密&#xff0c;防止第三方窃听或篡改信息。在选择SSL证书时&#xff0c;常见的有DV证书和OV证书&#xff0c;它们在验证标准和信任级别上有所不同。那么SSL证书DV和OV的有哪些…

TEC2083BS-PD码转换器(解决博世矩阵控制PELCO派尔高球机的问题)

TEC2083BS-PD码转换器 使用说明 1.设备概述 控制码转换器在安防工程中起着非常重要的角色&#xff0c;随着高速球型摄像机在安防工程中大范围的使用&#xff0c;而高速球厂家都因为某些原因很少使用博世、飞利浦的协议。为此&#xff0c;工程商经常会遇到博世协议和PELCO协议之…

【Oracle 数据库 SQL 语句 】积累1

Oracle 数据库 SQL 语句 1、分组之后再合计2、显示不为空的值 1、分组之后再合计 关键字&#xff1a; grouping sets &#xff08;&#xff08;分组字段1&#xff0c;分组字段2&#xff09;&#xff0c;&#xff08;&#xff09;&#xff09; select sylbdm ,count(sylbmc) a…

Vue [Day6]

路由进阶 路由模块的封装抽离 src/router/index.js import VueRouter from vue-router // 用绝对路径的方式来写目录 相当于src import Find from /views/Find import Friend from ../views/Friend import My from ../views/Myimport Vue from vue Vue.use(VueRouter)con…

Idea 反编译jar包

实际项目中&#xff0c;有时候会需要更改jar包源码来达到业务需求&#xff0c;本文章将介绍一下如何通过Idea来进行jar反编译 1、Idea安装decompiler插件 2、找到decompiler插件文件夹 decompiler插件文件夹路径为&#xff1a;idea安装路径/plugins/java-decompiler/lib 3、…

移动端的Flex布局

目录 引入 一、传统布局与flex布局 传统性 flex布局 二、felx的特点 三、flex布局父项的常见属性 四、flex布局子项的常见方向 总结 引入 flex 是 flexible Box的缩写&#xff0c;意为“弹性布局”&#xff0c;用来为盒状模型提供最大的灵活性&#xff0c;任何一个容器…

成像质量高精度标定高均匀光源积分球

随着航天遥感技术的发展&#xff0c;对遥感仪器的定标精度要求越来越高&#xff0c;这就需要高精度的工程应用定标光源。光学定标&#xff0c;在工程应用上是采用光学标准传递的方法对应用设备进行定标&#xff0c;而不是直接用原始标准对应用设备进行定标。其传递链路之一&…

树莓派安装ubuntu

ubuntu包下载 从ubuntu 官网下载镜像&#xff1a;https://cn.ubuntu.com/blog/build-raspberry-pi-desktop-ubuntu 按个人需求下载&#xff0c;可以首先使用 桌面版22.04 LTS版本&#xff1b; 烧录 从树莓派管官网下载image烧录工具&#xff1a;https://www.raspberrypi.c…

Improved Deep Metric Learning with Multi-class N-pair Loss Objective

Improved Deep Metric Learning with Multi-class N-pair Loss Objective 来源&#xff1a; NIPS’2016NEC Laboratories America 文章目录 Improved Deep Metric Learning with Multi-class N-pair Loss ObjectiveDistance Metric LearningDeep Metric Learning with Multip…

实战:使用Docker部署Hadoop集群

文章目录 Hadoop简介Hadoop优势Hadoop应用场景docker与docker-compose安装Hadoop集群搭建环境变量docker-compose环境文件树结构编排并运行容器运行wordcount例子 写在最后 Hadoop简介 Hadoop是一个由Apache基金会所开发的分布式系统基础架构。用户可以在不了解分布式底层细节…

ChatGLM2-6B在windows下的部署

2023-08-10 ChatGLM2-6B在windows下的部署 一、部署环境 1、Windows 10 专业版&#xff0c; 64位&#xff0c;版本号&#xff1a;22H2&#xff0c;内存&#xff1a;32GB 2、已安装CUDA11.3 3、已安装Anaconda3 64bit版本 4、有显卡NVIDIA GeForce RTX 3060 Laptop GPU …

AI Deep Reinforcement Learning Autonomous Driving(深度强化学习自动驾驶)

AI Deep Reinforcement Learning Autonomous Driving&#xff08;深度强化学习自动驾驶&#xff09; 背景介绍研究背景研究目的及意义项目设计内容算法介绍马尔可夫链及马尔可夫决策过程强化学习神经网络 仿真平台OpenAI gymTorcs配置GTA5 参数选择行动空间奖励函数 环境及软件…

8.10CPI决战日来临,黄金会意外走高吗?

近期有哪些消息面影响黄金走势&#xff1f;黄金多空该如何研判&#xff1f; ​黄金消息面解析&#xff1a;周四(8月10日)亚市早盘&#xff0c;美元指数在102.50维持多头走势&#xff0c;黄金避险情绪消散&#xff0c;金价跌至1916美元&#xff0c;下破1900美元前景深化。周三黄…

如何使用Audition生成固定频率的正弦波

一&#xff0c;简介 本文主要介绍如何使用Audition软件生成固定频率的正弦波进行相关测试验证工作。 二&#xff0c;准备工作 需要安装Audition软件&#xff0c;本次使用的是Adobe Audition CC 2018绿色版。其他版本也都可以&#xff0c;只是步骤上可能有细微的差别。 三&…

山西电力市场日前价格预测【2023-08-11】

日前价格预测 预测明日&#xff08;2023-08-11&#xff09;山西电力市场全天平均日前电价为367.15元/MWh。其中&#xff0c;最高日前电价为408.91元/MWh&#xff0c;预计出现在20: 00。最低日前电价为343.90元/MWh&#xff0c;预计出现在02: 30。 价差方向预测 1&#xff1a; 实…