我如何重组这些数据以匹配其原始 un-flattened 形状?
How can I restructure this data to match it's original un-flattened shape?
我有以下数据模型:
新模式
[
{
name : 'Tony',
id : 'Tony_id'
},{
name: 'Barry',
id: 'Barry_id',
parentId: 'Tony_id'
},{
name: 'George',
id: 'George_id',
parentId: 'Barry_id'
},{
name : 'Laura',
id : 'Laura_id',
parentId: 'Barry_id'
},{
name: 'Edward',
id: 'Edward_id'
},{
name: 'Patrick',
id: 'Patrick_id',
parentId: 'Edward_id'
}
]
所以结构是parents、children和grandchildren。最初模型如下所示,但我不得不将其展平:
旧型号
[
{
name : 'Tony',
id : 'Tony_id',
children: [
{
name: 'Barry',
id: 'Barry_id',
parentId: 'Tony_id',
children: [
{
name: 'George',
id: 'George_id',
parentId: 'Barry_id'
},{
name : 'Laura',
id : 'Laura_id',
parentId: 'Barry_id'
}
]
}
]
},{
name: 'Edward',
id: 'Edward_id',
children: [
{
name: 'Patrick',
id: 'Patrick_id',
parentId: 'Edward_id'
}
]
}
]
我丢失了对旧模型的任何引用。
只使用新模型,如何重组它以匹配我的旧模型,到un-flatten呢?
你可以递归地做:
var newData = [
{
name : 'Tony',
id : 'Tony_id',
children: [
{
name: 'Barry',
id: 'Barry_id',
parentId: 'Tony_id',
children: [
{
name: 'George',
id: 'George_id',
parentId: 'Barry_id'
},{
name : 'Laura',
id : 'Laura_id',
parentId: 'Barry_id'
}
]
}
]
},{
name: 'Edward',
id: 'Edward_id',
children: [
{
name: 'Patrick',
id: 'Patrick_id',
parentId: 'Edward_id'
}
]
}
];
function flat(datas, flatten) {
datas.forEach(el => {
flatten.push(el);
if (el.children) {
flat(el.children, flatten);
delete el.children;
}
});
}
var flatten = [];
flat(newData, flatten);
console.log(flatten);
编辑:反向操作:
var data = [{ name: 'Tony', id: 'Tony_id' }, { name: 'Barry', id: 'Barry_id', parentId: 'Tony_id' }, { name: 'George', id: 'George_id', parentId: 'Barry_id' }, { name: 'Laura', id: 'Laura_id', parentId: 'Barry_id' }, { name: 'Edward', id: 'Edward_id' }, { name: 'Patrick', id: 'Patrick_id', parentId: 'Edward_id' }];
function ToTree(arrayItems) {
var map = {}, roots = [];
arrayItems.forEach((item, i) => {
map[item.id] = i;
item.children = [];
});
arrayItems.forEach(node => {
if (node.parentId && arrayItems[map[node.parentId]]) {
arrayItems[map[node.parentId]].children.push(node);
} else {
roots.push(node);
}
});
return roots;
}
var myTree = ToTree(data);
console.log(myTree);
您可以构建一个带有 object 的树来保持 parents 和 children 关系。
此提议也适用于未排序的数据。
var data = [{ name: 'Tony', id: 'Tony_id' }, { name: 'Barry', id: 'Barry_id', parentId: 'Tony_id' }, { name: 'George', id: 'George_id', parentId: 'Barry_id' }, { name: 'Laura', id: 'Laura_id', parentId: 'Barry_id' }, { name: 'Edward', id: 'Edward_id' }, { name: 'Patrick', id: 'Patrick_id', parentId: 'Edward_id' }],
tree = function (data, root) {
var r = [], o = {};
data.forEach(function (a) {
if (o[a.id] && o[a.id].children) {
a.children = o[a.id] && o[a.id].children;
}
o[a.id] = a;
if (a.parentId === root) {
r.push(a);
} else {
o[a.parentId] = o[a.parentId] || {};
o[a.parentId].children = o[a.parentId].children || [];
o[a.parentId].children.push(a);
}
});
return r;
}(data, undefined);
console.log(tree);
console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }
和(为了好玩)相反:
let oldData = [
{name : 'Tony', id : 'Tony_id'},
{name: 'Barry', id: 'Barry_id', parentId: 'Tony_id'},
{name: 'George', id: 'George_id', parentId: 'Barry_id'},
{name : 'Laura', id : 'Laura_id', parentId: 'Barry_id'},
{name: 'Edward', id: 'Edward_id'},
{name: 'Patrick', id: 'Patrick_id', parentId: 'Edward_id'}
]
// First we need a Key-Data object with :
// Key : person's id
// Value : person's data
let dwKeys = {}
oldData.forEach( d => dwKeys[d.id] = d) ;
// The same objects with children
let dwChildren = {} ;
// Then we can know who's who
for(let uid in dwKeys)
{
// We take the person's data
let udata = dwKeys[uid] ;
// we take the parent (if any)
let parentId = udata.parentId ;
// No parent ? OK => root person
if ( ! parentId ) {
dwChildren[uid] = udata ;
continue ;
}
// Now, we add the child to their parent
// Do the record if needed
if ( undefined === dwChildren[parentId] ){
dwChildren[parentId] = dwKeys[parentId] ;
}
// Do the children field if needed
if (undefined === dwChildren[parentId]['children'] ){
dwChildren[parentId]['children'] = [];
}
// Add this child
delete udata.parentId ;
dwChildren[parentId]['children'].push(udata);
}
// Hey no, it doesn't work:
// dwChildren = dwChildren.values() ;
// So:
let awChildren = [] ; // for "Array With Children"
for (let uid in dwChildren ) { awChildren.push(dwChildren[uid]) }
console.log(awChildren);
.as-console-wrapper { max-height: 100% !important; top: 0; }
我有以下数据模型:
新模式
[
{
name : 'Tony',
id : 'Tony_id'
},{
name: 'Barry',
id: 'Barry_id',
parentId: 'Tony_id'
},{
name: 'George',
id: 'George_id',
parentId: 'Barry_id'
},{
name : 'Laura',
id : 'Laura_id',
parentId: 'Barry_id'
},{
name: 'Edward',
id: 'Edward_id'
},{
name: 'Patrick',
id: 'Patrick_id',
parentId: 'Edward_id'
}
]
所以结构是parents、children和grandchildren。最初模型如下所示,但我不得不将其展平:
旧型号
[
{
name : 'Tony',
id : 'Tony_id',
children: [
{
name: 'Barry',
id: 'Barry_id',
parentId: 'Tony_id',
children: [
{
name: 'George',
id: 'George_id',
parentId: 'Barry_id'
},{
name : 'Laura',
id : 'Laura_id',
parentId: 'Barry_id'
}
]
}
]
},{
name: 'Edward',
id: 'Edward_id',
children: [
{
name: 'Patrick',
id: 'Patrick_id',
parentId: 'Edward_id'
}
]
}
]
我丢失了对旧模型的任何引用。
只使用新模型,如何重组它以匹配我的旧模型,到un-flatten呢?
你可以递归地做:
var newData = [
{
name : 'Tony',
id : 'Tony_id',
children: [
{
name: 'Barry',
id: 'Barry_id',
parentId: 'Tony_id',
children: [
{
name: 'George',
id: 'George_id',
parentId: 'Barry_id'
},{
name : 'Laura',
id : 'Laura_id',
parentId: 'Barry_id'
}
]
}
]
},{
name: 'Edward',
id: 'Edward_id',
children: [
{
name: 'Patrick',
id: 'Patrick_id',
parentId: 'Edward_id'
}
]
}
];
function flat(datas, flatten) {
datas.forEach(el => {
flatten.push(el);
if (el.children) {
flat(el.children, flatten);
delete el.children;
}
});
}
var flatten = [];
flat(newData, flatten);
console.log(flatten);
编辑:反向操作:
var data = [{ name: 'Tony', id: 'Tony_id' }, { name: 'Barry', id: 'Barry_id', parentId: 'Tony_id' }, { name: 'George', id: 'George_id', parentId: 'Barry_id' }, { name: 'Laura', id: 'Laura_id', parentId: 'Barry_id' }, { name: 'Edward', id: 'Edward_id' }, { name: 'Patrick', id: 'Patrick_id', parentId: 'Edward_id' }];
function ToTree(arrayItems) {
var map = {}, roots = [];
arrayItems.forEach((item, i) => {
map[item.id] = i;
item.children = [];
});
arrayItems.forEach(node => {
if (node.parentId && arrayItems[map[node.parentId]]) {
arrayItems[map[node.parentId]].children.push(node);
} else {
roots.push(node);
}
});
return roots;
}
var myTree = ToTree(data);
console.log(myTree);
您可以构建一个带有 object 的树来保持 parents 和 children 关系。
此提议也适用于未排序的数据。
var data = [{ name: 'Tony', id: 'Tony_id' }, { name: 'Barry', id: 'Barry_id', parentId: 'Tony_id' }, { name: 'George', id: 'George_id', parentId: 'Barry_id' }, { name: 'Laura', id: 'Laura_id', parentId: 'Barry_id' }, { name: 'Edward', id: 'Edward_id' }, { name: 'Patrick', id: 'Patrick_id', parentId: 'Edward_id' }],
tree = function (data, root) {
var r = [], o = {};
data.forEach(function (a) {
if (o[a.id] && o[a.id].children) {
a.children = o[a.id] && o[a.id].children;
}
o[a.id] = a;
if (a.parentId === root) {
r.push(a);
} else {
o[a.parentId] = o[a.parentId] || {};
o[a.parentId].children = o[a.parentId].children || [];
o[a.parentId].children.push(a);
}
});
return r;
}(data, undefined);
console.log(tree);
console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }
和(为了好玩)相反:
let oldData = [
{name : 'Tony', id : 'Tony_id'},
{name: 'Barry', id: 'Barry_id', parentId: 'Tony_id'},
{name: 'George', id: 'George_id', parentId: 'Barry_id'},
{name : 'Laura', id : 'Laura_id', parentId: 'Barry_id'},
{name: 'Edward', id: 'Edward_id'},
{name: 'Patrick', id: 'Patrick_id', parentId: 'Edward_id'}
]
// First we need a Key-Data object with :
// Key : person's id
// Value : person's data
let dwKeys = {}
oldData.forEach( d => dwKeys[d.id] = d) ;
// The same objects with children
let dwChildren = {} ;
// Then we can know who's who
for(let uid in dwKeys)
{
// We take the person's data
let udata = dwKeys[uid] ;
// we take the parent (if any)
let parentId = udata.parentId ;
// No parent ? OK => root person
if ( ! parentId ) {
dwChildren[uid] = udata ;
continue ;
}
// Now, we add the child to their parent
// Do the record if needed
if ( undefined === dwChildren[parentId] ){
dwChildren[parentId] = dwKeys[parentId] ;
}
// Do the children field if needed
if (undefined === dwChildren[parentId]['children'] ){
dwChildren[parentId]['children'] = [];
}
// Add this child
delete udata.parentId ;
dwChildren[parentId]['children'].push(udata);
}
// Hey no, it doesn't work:
// dwChildren = dwChildren.values() ;
// So:
let awChildren = [] ; // for "Array With Children"
for (let uid in dwChildren ) { awChildren.push(dwChildren[uid]) }
console.log(awChildren);
.as-console-wrapper { max-height: 100% !important; top: 0; }