Vue2监听对象变化,方便调试代码

比较好的是方法2

方法一,直接监听list.list2

watch:{
    'list.list2': {
        handler(newVal, oldVal) {
            debugger;
        },
        deep: true,
        immediate: false,
        sync: true
    }
}

deep是用来监听对象内部变化,监听数组变更不需要设置,但是如果数组内还是个对象就需要了
immediate 文档里说将立即以表达式的当前值触发回调,没看懂变化,如果是个基本对象好像在生命周期initState时会调用一次
sync是个不在文档里出现的选项,设置之后调用栈里就不会是promise.then,而是直接调用到handler位置,相当于监听提前于$nextTick进行. 我们项目代码用了很奇怪的方法,所以如果不加sync调用栈里找不到源码位置,加入后就可以在调用栈中查看修改这条数据时是哪句源码进行的, 测试代码看不到这个问题.

缺陷: newVal和oldVal永远相同,因为是个对象,所以内存地址相同

方法2

computed结合watch

{
    computed:{
        computedObjectToBeWatched() {
            return JSON.stringify(this.list.list2);
        }
    },
    watch:{
        computedObjectToBeWatched: {
            deep: true,
            handler(newVal, oldVal) {
                if (newVal !== oldVal) {
                    debugger;
                }
            }
        }
    }
}

由上面的方法1知道在handler时拦截的变量地址是相同的,那就先用computed将old设置为一个不相同的变量,比如直接转为JSON,这样在watch比较时就是两个字符串进行比较了,而且比较的方法比较粗暴是单纯的比较,也可以写的更精准,比如每个对象的数据进行比较.

写作原因

因为项目历史原因,代码比较复杂,各个地方可能都会直接修改data的数据,这时候可能就不知道触发的是哪条代码导致对象进行了修改,所以上网寻找一些调试方法,最原始的方法就是读代码直接看,而用vue的watch才是更简单的方法.

基本代码如下:

<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    <div id="app">
        <template>
            <div v-for="item in list.list2">
                <span>{{item.show}} {{item.name}}</span>
            </div>
            <button @click="set">切换</button>
        </template>
    </div>
</body>

</html>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
<script>
    var app = new Vue({
        el: '#app',
        data: {
            list: {
                list2: [
                    { id: 0, show: true, name: '张三' },
                    { id: 1, show: false, name: '李四' },
                    { id: 2, show: true, name: '王五' }
                ]
            }
        },
        methods:{
            set: function(){
                this.list.list2[0].show = !this.list.list2[0].show
            }
        },
        computed:{
        },
        watch: {
        }
    })
</script>

点击切换按钮,list的list2的第一个show就会改变,我的项目有多层对象,就用多层对象做示例了

来源: Stack Overflow链接

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值