在很多场景下由于区分授权,比如菜单或组织机构等,给当前用户返回的往往可能不是以固定的父id来标识数据的根节点。这种情况下就需要动态的根据当前数组本身自动判断构造树。
理论就是根据父id,在数组或树中查找,如果在元素中找到对应id,那么就追加为子元素。如果找不到,那当前元素就是定级元素。
/**
* 列表转为树,pid值未知。思路:第一遍遍历构造为map,第二遍
* @param {*} list
* @returns
*/
export function listToTree(list) {
let treeData = []
// 第一次遍历,构造一个map
let tmpObj = {}
list.forEach(item => { // 这里也可以把值设置为数组的索引,这样的话在这里可以不必存储这么大空间了
tmpObj[item.id] = item
});
list.forEach(v => {
const parent = tmpObj[v.parentId]
// 如果有parentId并且在临时map中存在
if (v.parentId && parent) {
// 那么把当前元素追加到目标元素children之内,并且把当前key删除
if (!parent.children) {
parent.children = []
}
parent.children.push(v)
} else {
treeData.push(v)
}
})
// 再遍历,根据pid在map中找是否有key,如果有,说明是上级,那么追加到children中;如果没有,那么就跳过,表示没有上级
return treeData;
}