今天分享一个自己实现的基于 TypeScript 的将列表转为树形列表的通用函数。
/** * 将一个列表转化为树形列表, 列表数据需要本身支持转化成数型 * @param list 列表数据 * @param equalLevalItem 判断两个列表项是否同级且不相等的回调函数 * @param listFirstIsRoot 使用列表中的第1项作为树的root节点 * @param isRootItem 判断列表项是否为root节点的回调函数,listFirstIsRoot = false 时有效 * @param childrenField 列表项中,存放 children 列表的字段名称 * @param childrenMust 子列表字段是否必须存在,为 true 时,如果没有子列表,会将其设置为 [] * @param item 当前列表项, 调用者传 undefined * @returns */ // eslint-disable-next-line max-params static toTreeList<T>( list?: T[], equalLevalItem?: (a: T | undefined, item: T) => boolean, listFirstIsRoot: boolean = true, isRootItem?: (e: T, index: number) => boolean, childrenField: string = "children", childrenMust: boolean = false, item?: T, ): T[] { const children: T[] = [] if (! list || list.length === 0) { return children } const handleChildren = (e: T) => { let srcData = e[childrenField]; if (childrenMust && ! srcData) { srcData = [] e[childrenField] = srcData } const data: T[] | undefined = srcData ? srcData as T[] : [] data.push(...this.toTreeList(list, equalLevalItem, listFirstIsRoot, undefined, childrenField, childrenMust, e)) if (! srcData && data.length > 0) { e[childrenField] = data; } else if (data.length === 0 && ! childrenMust) { e[childrenField] = undefined } } let v = item if (v === undefined) { if (listFirstIsRoot) { v = list[0] if (v[childrenField] === undefined) { v[childrenField].children = [] } handleChildren(v) children.push(v) } else { // 找出 root 项 list.forEach((e, index) => { if (isRootItem?.(e, index)) { handleChildren(e) children.push(e) } }) } return children } list.filter((e) => { if (equalLevalItem?.(item, e)) { return e } // 排除掉当前 item }).forEach((e) => { handleChildren(e) children.push(e) }) return children }
使用示例:
Utils.toTreeList( list, (src, item) => src?.id === item.pid && src.id !== item.id, false, (item, idx) => item.pid === 0 )
查看更多关于将一个列表转为树形列表的函数(通用型)的详细内容...
声明:本文来自网络,不代表【好得很程序员自学网】立场,转载请注明出处:http://www.haodehen.cn/did223445