Vue,如何处理深度嵌套对象的React性

pprl5pva  于 2023-10-23  发布在  Vue.js
关注(0)|答案(1)|浏览(148)

我有一个我正在操作的对象,如下所示:

const posts = [
    { key1: "abc", key2: [{ innerKey1: "def", innerKey2: 123 }, { innerKey1: "def", innerKey2: 123 }] },
    { key1: "abc", key2: [{ innerKey1: "def", innerKey2: 123 }, { innerKey1: "def", innerKey2: 123 }] },
    { key1: "abc", key2: [{ innerKey1: "def", innerKey2: 123 }, { innerKey1: "def", innerKey2: 123 }] },
];

posts[0].key2[1].innerKey1 = "newVal";

key2中的Array是一个prop,内部键预计会发生变化。我想在innerKey1innerKey2发生变化时保持React性。
因为Vue很难检测到数组和对象的变化,我们不能直接通过索引修改数组或通过键修改对象。
为了保持React性,似乎我们需要一些复杂的逻辑,使用Vue.set()来设置newVal
我在想沿着这条线:
Vue.set(posts, 1, Vue.set(key2, 0, Vue.set(innerKey1, "newVal")))
这是保持React性的最佳方法吗,还是我遗漏了什么可以让这更容易?
注意:我还尝试在子组件中使用深度观察器来观察key2数组中发生的更改。但它似乎无法观察到这些变化。

//ChildComponent.vue
<html>
  <div>
   <RandomComponent v-for="thing in key2" :key... :innerKey2="thing.innerKey2">
  </div>
</html>

<script>
props: {
    key2: {
        type: Array,
        require: true,
    },
},
watch: {
    key2: {
        immediate: true,
        deep: true,
        handler () {
            console.log("Watcher working"); //Does not fire when parent mutates innerKeys
        },
    },
},
</script>
djmepvbi

djmepvbi1#

我觉得这个问题不够明确。

  • 如果你只想更新**现有数组元素的一个属性,**通过索引改变应该可以正常工作,没有任何解决办法。

即,这应该是React性的

posts[0].key2[1].innerKey1 = "newVal";
  • 然而,如果你试图替换数组元素,你需要一个解决这里解释的VueReact性问题的方法。

我认为对于您的情况,最干净的解决方法是使用Array.splice来替换元素。(例如网络响应后)

const postId = 0 // the root element 
  const updatePost = { ...this.posts[postId] }
  updatePost.key2[1].innerKey1 = 'newVal'

  this.posts.splice(postId, 1, updatedPost);

这是我在codesanbox上制作的一个插图

相关问题