zoukankan      html  css  js  c++  java
  • vue中同一个页面多次使用同一个组件的相互干扰问题

    我们知道,vue有一个重要的理念就是组件化,即将重复使用的功能点抽提出来作为组件,需要使用的页面只需要引用该组件即可得到相应的功能点。

    而组件化的一个重要特性就是作用域隔离,即一个组件实例拥有一个私有的作用域,当在页面中引用了该组件之后,只有该组件实例能访问该作用域。

    但是当在同一个页面多次使用同一个组件的时候,如果只创建了一个实例,但是却对这个实例调用了两次,这两个调用就会造成相互干扰的问题,因为这时候这两个调用访问的是同一个作用域。比如有现在有一个yanggb组件,我引入到我的页面中(创建了一个组件实例),然后调用两次(在页面上调用组件实例两次),那么当我给第一个调用绑定的对象变量的一个属性赋值了100,那么第二个调用绑定的同一个对象变量的该属性也会被赋值100,因为这两个调用在同一个作用域内绑定了同一个对象变量,而JavaScript内一切对象皆为引用,也就导致第二个调用的值跟着第二个调用的值变化了。

    // 引用yanggb组件并创建一个实例
    const yanggb = () => import('@/components/yanggb')
    // 注册该组件实例
    components: { yanggb }
    // 在页面上两次调用该组件实例
    <yanggb :value="100"></yanggb>
    <yanggb></yanggb>

    这个时候,如果该组件是直接显示的:value属性中绑定的值的话,那么两个调用都会显示100的值。

    其实解决办法在这里已经呼之欲出了,既然创建一个实例调用两次会相互影响,那么我创建两个实例分别调用一次不就不会相互干扰了吗?我们来试一下。

    // 引用同一个yanggb组件但创建两个个实例
    const yanggb = () => import('@/components/yanggb')
    const yanggb1 = () => import('@/components/yanggb')
    // 注册两个组件实例
    components: { yanggb, yanggb1 }
    // 在页面上分别调用两个组件实例
    <yanggb :value="100"></yanggb>
    <yanggb1></yanggb1>

    那么这个时候因为两个实例拥有相互独立的私有作用域,也就不会导致相互干扰的结果了,第二个实例的调用不会显示100的值。

    PS:以上的【实例】和【调用】相关字眼是个人的理解,只是为了方便理解,并不一定正确。

    另外,在解决问题的过程中,查到一些相关的解决方案,其中一个是使用JSON.stringify()和JSON.parse()两个方法配合使用来RE-双向绑定(个人理解是强行派生出新的对象,解除对原对象的引用,并将该新对象绑定到该组件调用上),但是总觉得有点奇怪,因为这样只是在同一个作用域内解除了对同一个对象的多次引用,不太符合组件化的设计理念与特性,并可能产生意料之外的问题,不是很喜欢这种方法。

    "很多人都在告诉我要懂事,但是没有一个人告诉我要快乐。"

  • 相关阅读:
    线性回归损失函数求解
    【线性代数】四个基本子空间
    【线性代数】如何寻找一个投影矩阵
    【hihoCoder】#1133 : 二分·二分查找之k小数
    [LeetCode解题报告] 502. IPO
    [LeetCode解题报告] 703. 数据流中的第K大元素
    【排序】堆排序
    全文检索以及Lucene的应用
    MySql优化之mycat
    MySql优化之主从复制
  • 原文地址:https://www.cnblogs.com/yanggb/p/12431367.html
Copyright © 2011-2022 走看看