扁平化
// 树形扁平化
export const treeDataToPlanishData = (list, parent, level = 0, clues = []) => { // eslint-disable-line
return list.reduce((prev, {
children = [],
...rest
}) => {
const parentKey = parent || '';
const keyClues = clues.concat(rest.key);
return prev.concat({ ...rest,
parentKey,
level,
isLeaf: !!parentKey,
keyClues,
}, treeDataToPlanishData(children, rest.key, level + 1, keyClues));
}, []);
};
// while 递归
function toArray(data, result = { nodes: [], edges: [] }, pid) {
if (!data.root) {
return result;
}
const nodeId = data.root.id;
result.nodes.push({
id: nodeId,
});
if (pid) {
result.edges.push({
id: Math.random(),
target: nodeId,
source: pid,
});
}
if (data.children) {
while (data.children.length) {
const pop = data.children.pop();
toArray(pop, result, nodeId);
}
}
return result;
}
// 递归
function toArray(data, result = { nodes: [], edges: [] }, pid) {
if (!data.root) {
return result;
}
const nodeId = data.root.id ?? Math.random();
result.nodes.push({
id: nodeId,
pid,
});
if (pid) {
result.edges.push({
id: Math.random(),
source: pid,
target: nodeId,
});
}
if (data.children) {
data.children.forEach((item) => {
toArray(item, result, nodeId);
});
}
return result;
}
转树形
对象
export const planishDataToTreeData = (data) => {
const idMap = {};
const jsonTree = [];
data.forEach((v) => {
idMap[v.key] = v;
});
data.forEach((v) => {
const parent = idMap[v.parentKey];
if (parent) {
parent.children = parent.children || [];
parent.children.push(v);
} else {
jsonTree.push(v);
}
});
return jsonTree;
};
JS 实现扁平化数据结构和tree 转化 ```typescript function arrayToTree(items) { let res = [] // 存放结果集 let map = {} // 判断对象是否有某个属性 let getHasOwnProperty = (obj, property) => Object.prototype.hasOwnProperty.call(obj, property)
// 边做map存储,边找对应关系 for (const i of items) {
map[i.id] = { ...i, children: getHasOwnProperty(map, i.id) ? map[i.id].children : [] } const newItem = map[i.id] if (i.pid === 0) { res.push(newItem) } else { if (!getHasOwnProperty(map, i.pid)) { map[i.pid] = { children: [] } } map[i.pid].children.push(newItem) }
} return res }
```typescript
const createDataTree = (dataset) => {
const hashTable = Object.create(null);
dataset.forEach(
(aData) => (hashTable[aData.id] = { ...aData, children: [] })
);
const dataTree = [];
dataset.forEach((aData) => {
if (aData.pid) {
hashTable[aData.pid].children.push(hashTable[aData.id]);
} else {
dataTree.push(hashTable[aData.id]);
}
});
return dataTree;
};
function list_to_tree(list) {
var map = {},
node,
roots = [],
i;
for (i = 0; i < list.length; i += 1) {
map[list[i].id] = i; // initialize the map
list[i].children = []; // initialize the children
}
for (i = 0; i < list.length; i += 1) {
node = list[i];
if (node.parentId !== '0') {
// if you have dangling branches check that map[node.parentId] exists
list[map[node.parentId]].children.push(node);
} else {
roots.push(node);
}
}
return roots;
}
filter
function setTreeData(data) {
/** 对源数据深度克隆 */
const cloneData = JSON.parse(JSON.stringify(data));
const tree = cloneData.filter((father) => {
/** 循环所有项 并获取当前项为 为 child.pid */
const branchArr = cloneData.filter((child) => father.id == child.pid);
if (branchArr.length > 0) {
/** 如果存在子级,则给父级添加一个children属性,并赋值 */
father.children = branchArr;
}
return father.pid == undefined; //返回第一层
});
return tree; //返回树形数据
}
- Build tree array from flat array in javascript
- 扁平数组和树形结构的相互转换
- 面试了十几个高级前端,竟然连(扁平数据结构转Tree)都写不出来
- JS 实现扁平化数据结构和tree 转化
export const traverseTree = (
data: ServiceData,
result: NsGraph.IGraphData = { nodes: [], edges: [] },
parentId: string = '',
) => {
if (!data.rootNode) {
return result;
}
const sourceNodeId = data.rootNode.id ?? uuidv4();
const nodeConfig = {
parentId,
...data.rootNode,
id: sourceNodeId,
primitiveType: data.rootNode.type,
logicalGate: data.logicalGate ?? {},
// @ts-ignore
...getBaseEventNodeConfig(data.rootNode.type, Math.random() > 0.5), // data.rootNode.personal
};
result.nodes.push(nodeConfig);
/** 添加边 */
if (parentId) {
result.edges.push({
parentId,
id: uuidv4(),
source: parentId,
target: sourceNodeId,
});
}
/** 包含子节点 */
if (data.subTreeList) {
data.subTreeList.forEach((item) => {
traverseTree(item, result, sourceNodeId);
});
}
return result;
};
export const getHasOwnProperty = (obj: Record<string, any>, property: string) =>
Object.prototype.hasOwnProperty.call(obj, property);
const omitSpecifyKeys = (data: EventNodeData, keys: (keyof EventNodeData)[]) => omit(data, keys);
const FILTER_NODE_KEYS = ['height', 'width', 'logicalGate', 'x', 'y', 'renderKey', 'primitiveType'];
/** 实时获取画布节点数据生成对应树 */
export const buildAfterTree = (nodes: NsGraph.INodeConfig[]) => {
const res: ServiceData[] = [];
const map: Record<string, ServiceData> = {};
for (const node of nodes) {
const rootNode = omitSpecifyKeys(node as EventNodeData, FILTER_NODE_KEYS);
map[node.id] = {
rootNode: { ...rootNode, type: node.primitiveType } as EventNodeData,
logicalGate: node.logicalGate,
subTreeList: getHasOwnProperty(map, node.id) ? map[node.id].subTreeList : [],
};
const newItem = map[node.id];
if (!node.parentId) {
res.push(newItem);
} else {
if (!getHasOwnProperty(map, node.parentId)) {
map[node.parentId] = {
subTreeList: [],
rootNode: node as EventNodeData,
logicalGate: node.logicalGate,
};
}
map[node.parentId].subTreeList?.push(newItem);
}
}
return res[0];
};