Uncaught (in promise) Maximum recursive updates exceeded. This means you have

vue yekong

vue项目运行时,报了下面的错误:

Uncaught (in promise) Maximum recursive updates exceeded. This means you have a reactive effect that is mutating its own dependencies and thus recursively triggering itself. Possible sources include component template, render function, updated hook or watcher source function

原代码

<template>
  <div class="itemBodys hideScrollBar">
    <Vue3SeamlessScroll :step="0.5" :wheel="true" :hover="true" :list="sortList" class="tableBody">
      <div class="list">
        <div class="listItem" v-for="(item,index) in sortList" :key="index">
          <div class="listItemTop">
            <div class="icon" :style="getIconBackground(index)">
              {{ index + 1 }}
            </div>
            <span class="name">{{ item.name }}</span>
          </div>
          <div class="listItemBottom">
            <progressBar :index="index" :total="total" :item="item"></progressBar>
          </div>
        </div>
      </div>
    </Vue3SeamlessScroll>
  </div>
</template>

<script>
import progressBar from './components/progressBar.vue'
import ranking4 from './components/assets/ranking4.png'
import ranking1 from './components/assets/ranking1.png'
import ranking2 from './components/assets/ranking2.png'
import ranking3 from './components/assets/ranking3.png'
import {Vue3SeamlessScroll} from "vue3-seamless-scroll";

export default {
  name: "title",
  data() {
    return {
      list: []
    }
  },
  components: {progressBar,Vue3SeamlessScroll},
  props: {
    // 类型 0所有数据累加作为基数进行占比计算  1取数据中最大的数值作为基数进行计算
    type: {
      type: Number,
      default() {
        return 1;
      }
    },
  },
  computed: {
    sortList: function () {
      return this.sortKey(this.list, 'value')
    },
    total: function () {
      var total = 0
      if (this.type == 0) {
        total = this.getTotalByKey(this.list, 'value')
      } else {
        total = this.getMaxNumByKey(this.list, 'value')
      }
      return total
    },
  },
  mounted() {
    this.getData()
  },
  methods: {
    getIconBackground(index) {
      let imageUrl = ranking4; // 默认图片
      if (index === 0) {
        imageUrl = ranking1;
      } else if (index === 1) {
        imageUrl = ranking2;
      } else if (index === 2) {
        imageUrl = ranking3;
      }
      return `background: url(${imageUrl}) no-repeat; background-size: 100% 100%;`;
    },
    async getData() {
      function generateRandomArray() {
        const names = [
          "计算机科学与技术",
          "人工智能",
          "供应链管理",
          "历史学",
          "理学",
          "工程学",
          "文学",
          "教育学",
          "经济学",
          "艺术",
          "公共健康",
          "商学"
        ];

        const result = names.map(name => {
          return {
            name: name,
            value: Math.floor(Math.random() * (200 - 100 + 1)) + 100
          };
        });

        return result;
      }

      this.list = generateRandomArray();
    },
    sortKey(array, key) {
      var list = array.sort(function (a, b) {
        var x = a[key];
        var y = b[key];
        return ((x < y) ? -1 : (x > y) ? 1 : 0)
      })
      return list.reverse()
    },
    getMaxNumByKey(list, key) {
      var maxNum = list[0][key];
      list.forEach((type) => {
        if (type[key] > maxNum) {
          maxNum = type[key]
        }
      });
      return maxNum
    },
    getTotalByKey(list, key) {
      var total = 0;
      list.forEach((type) => {
        total = total + type[key]
      });
      return total
    },
  },
}
</script>

你遇到的错误 Maximum recursive updates exceeded 表明在你的 Vue.js 组件中存在一个无限递归更新的问题。这个问题通常是由于某个响应式数据的变化触发了自身的更新,从而导致无限循环。

在你的代码中,可能的原因包括以下几个方面:

  1. sortList 计算属性sortList 是一个计算属性,它依赖于 this.list。如果 this.list 的变化会触发 sortList 的重新计算,而 sortList 的重新计算又会触发 this.list 的变化,就会导致无限循环。

  2. total 计算属性total 计算属性依赖于 this.listthis.type。如果 this.listthis.type 的变化会触发 total 的重新计算,而 total 的重新计算又会触发 this.listthis.type 的变化,也会导致无限循环。

解决方法

  1. 检查计算属性的依赖关系:确保计算属性的依赖关系不会导致无限循环。

  2. 避免在计算属性中直接修改依赖数据:计算属性应该是纯粹的计算,不应该直接修改依赖的数据。

  3. 使用 watch 监听数据变化:如果需要在数据变化时执行某些操作,可以使用 watch 而不是计算属性。

示例修改

以下是一些可能的修改建议:

  1. 确保 sortListtotal 计算属性不会直接修改 this.list
computed: {
  sortList() {
    return this.sortKey([...this.list], 'value'); // 使用拷贝的数组进行排序
  },
  total() {
    if (this.type === 0) {
      return this.getTotalByKey(this.list, 'value');
    } else {
      return this.getMaxNumByKey(this.list, 'value');
    }
  }
}
  1. 检查 sortKey 方法:确保 sortKey 方法不会直接修改 this.list
methods: {
  sortKey(array, key) {
    return array.slice().sort((a, b) => b[key] - a[key]); // 使用拷贝的数组进行排序
  },
  // 其他方法保持不变
}
  1. 使用 watch 监听 list 的变化
watch: {
  list(newList) {
    // 在这里执行需要的操作,而不是在计算属性中
  }
}

完整代码示例

<template>
  <div class="itemBodys hideScrollBar">
    <Vue3SeamlessScroll :step="0.5" :wheel="true" :hover="true" :list="sortList" class="tableBody">
      <div class="list">
        <div class="listItem" v-for="(item, index) in sortList" :key="index">
          <div class="listItemTop">
            <div class="icon" :style="getIconBackground(index)">
              {{ index + 1 }}
            </div>
            <span class="name">{{ item.name }}</span>
          </div>
          <div class="listItemBottom">
            <progressBar :index="index" :total="total" :item="item"></progressBar>
          </div>
        </div>
      </div>
    </Vue3SeamlessScroll>
  </div>
</template>

<script>
import progressBar from './components/progressBar.vue'
import ranking4 from './components/assets/ranking4.png'
import ranking1 from './components/assets/ranking1.png'
import ranking2 from './components/assets/ranking2.png'
import ranking3 from './components/assets/ranking3.png'
import { Vue3SeamlessScroll } from "vue3-seamless-scroll";

export default {
  name: "item6",
  data() {
    return {
      list: []
    }
  },
  components: { progressBar, Vue3SeamlessScroll },
  props: {
    type: {
      type: Number,
      default() {
        return 1;
      }
    },
  },
  computed: {
    sortList() {
      return this.sortKey([...this.list], 'value'); // 使用拷贝的数组进行排序
    },
    total() {
      if (this.type === 0) {
        return this.getTotalByKey(this.list, 'value');
      } else {
        return this.getMaxNumByKey(this.list, 'value');
      }
    }
  },
  mounted() {
    this.getData();
  },
  methods: {
    getIconBackground(index) {
      let imageUrl = ranking4; // 默认图片
      if (index === 0) {
        imageUrl = ranking1;
      } else if (index === 1) {
        imageUrl = ranking2;
      } else if (index === 2) {
        imageUrl = ranking3;
      }
      return `background: url(${imageUrl}) no-repeat; background-size: 100% 100%;`;
    },
    async getData() {
      function generateRandomArray() {
        const names = [
          "计算机科学与技术",
          "人工智能",
          "供应链管理",
          "历史学",
          "理学",
          "工程学",
          "文学",
          "教育学",
          "经济学",
          "艺术",
          "公共健康",
          "商学"
        ];

        return names.map(name => ({
          name: name,
          value: Math.floor(Math.random() * (200 - 100 + 1)) + 100
        }));
      }

      this.list = generateRandomArray();
    },
    sortKey(array, key) {
      return array.slice().sort((a, b) => b[key] - a[key]); // 使用拷贝的数组进行排序
    },
    getMaxNumByKey(list, key) {
      return Math.max(...list.map(item => item[key]));
    },
    getTotalByKey(list, key) {
      return list.reduce((total, item) => total + item[key], 0);
    }
  }
}
</script>

通过这些修改,可以避免无限递归更新的问题。如果问题仍然存在,请进一步检查代码中的其他部分,确保没有其他地方导致无限循环。

喜欢