首页 > 解决方案 > 如何有效且非阻塞地填充数组

问题描述

场景如下...

组件模板

<template>
  <div>
   <loader v-show="loading"></loader> // loading animation
   <div v-show="!loading">
     <div v-for="group in groups">
       {{group.name}}
       <div v-for="item in group.list">
         {{item.name}}
       </div>
     </div>
   </div>
  </div>
</template>

组件数据

data: function () {
    return {
        list: [],
        groups: [],
        loading: true
    }
}

1.从api获取一维数组

axios.get(API_URL).then(
    (response) => {
        this.list = response.data.payload;
    }
);

数组结构如下...

[
  {
    "name": "bob",
    "group": "A"
  },
  {
    "name": "sally",
    "group": "A"
  },
  {
    "name": "john",
    "group": "B"
  },
  {
    "name": "jane",
    "group": "B"
  },
]

2.使用每个项目的组属性将数组转换为二维

当前解决方案(阻塞!效率低下?

// loading animation stops at this point
this.list.forEach((item, index) => {
    let hasGroupChanged = false;
    if (index === 0) {
        hasGroupChanged = true;
    } else {
        let currentGroupName = item.group;
        let previousGroupName = this.list[index - 1].group;
        hasGroupChanged = previousGroupName !== currentGroupName;
    }
    if (hasGroupChanged) {
        const group = {
            group: item.group,
            list: []
        };
        this.groups.push(group);
    }
    const groupIndex = this.groups.length - 1;
    this.groups[groupIndex].list.push(item);
});

this.loading = false;

如何保持加载动画直到组被填充?

标签: javascriptarraysvue.jsasync-await

解决方案


您的“加载”动画被“冻结”,因为 JavaScript 是单线程的,并且当您的转换代码运行时(假设数据比示例中显示的多得多,因此它运行了很长时间),浏览器的呈现被阻止。

您可以优化转换代码以使其更快,或者您可以查看此 SO 答案以获取详细信息和解决方案,了解如何使长时间运行的操作不阻塞浏览器的渲染...。


推荐阅读