更好的解压对象阵列的解决方案
Better Solution for Unflattening Array of Objects
For the following array of Objects
[
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System","T3": "Audio","Prod": "Audio System","Mfr": "One"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System","T3": "Audio","Prod": "Audio System","Mfr": "Two"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System","T3": "Video","Prod": "Video System","Mfr": "Other"}
]
I intend to get a unflatten object like the one below :
[{
"Corp": "ABC",
"List": [{
"T1": "HW A/V",
"List": [{
"T2": "A/V System",
"List": [{
"T3": "Audio",
"List": [{
"Prod": "Audio System",
"List": [
{"Mfr": "One"},
{"Mfr": "Two"}
]
}]
},
{
"T3": "Video",
"List": [{
"Prod": "Video System",
"List": [
{"Mfr": "Other"}
]
}]
}]
}]
}]
}]
I did get the result I intend to get as described above. I used underscore to get the result. Following code snippet did the job for me :
var items = _.map(_.groupBy(itemList, 'Corp'), function (a) {
return _.extend(_.pick(a[0], 'Corp'), {
List: _.map(_.groupBy(a, 'T1'), function (b) {
return _.extend(_.pick(b[0], 'T1'), {
List: _.map(_.groupBy(b, 'T2'), function (c) {
return _.extend(_.pick(c[0], 'T2'), {
List: _.map(_.groupBy(c, 'T3'), function (d) {
return _.extend(_.pick(d[0], 'T3'), {
List: _.map(_.groupBy(d, 'Prod'), function (e) {
return _.extend(_.pick(e[0], 'Prod'), {
List: _.map(e, function (elem) {
return _.pick(elem, 'Mfr')
})
});
})
});
})
});
})
});
})
});
});
Now, So All I am looking for, is if someone can enhance my solution. I want to optimize both space and time for this process.
PS: In morning, I had asked a similar question requesting for the solution, and that question was marked as TOO BROAD and was put on HOLD, so I have added my solution with this question, now all I am looking for is a better solution.
谢谢
为了避免重叠语句,您可能需要定义一个 'expand keys' 列表并对其进行迭代。
用类似的东西自动提取密钥有点诱人:
expandKeys = _.keys(itemList[0]);
但由于 Javascript 不能保证对象中键的顺序,您确实应该显式定义此列表。
下面是一些示例代码。
var itemList = [
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System", "T3": "Audio", "Prod": "Audio System", "Mfr": "One"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System", "T3": "Audio", "Prod": "Audio System", "Mfr": "Two"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System", "T3": "Video", "Prod": "Video System", "Mfr": "Other"}
];
var expandKeys = [ 'Corp', 'T1', 'T2', 'T3', 'Prod', 'Mfr' ];
function expandList(list, keys) {
var node, obj, root = {};
_.each(list, function(item) {
obj = root;
_.each(keys, function(key) {
obj = (obj.List = obj.List || []);
node = _.find(obj, function(i) { return i[key] == item[key]; });
if(node === undefined) {
obj.push(node = {});
node[key] = item[key];
}
obj = node;
});
});
return root.List;
}
var res = expandList(itemList, expandKeys);
console.log(res);
<script src="http://underscorejs.org/underscore-min.js"></script>
For the following array of Objects
[
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System","T3": "Audio","Prod": "Audio System","Mfr": "One"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System","T3": "Audio","Prod": "Audio System","Mfr": "Two"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System","T3": "Video","Prod": "Video System","Mfr": "Other"}
]
I intend to get a unflatten object like the one below :
[{
"Corp": "ABC",
"List": [{
"T1": "HW A/V",
"List": [{
"T2": "A/V System",
"List": [{
"T3": "Audio",
"List": [{
"Prod": "Audio System",
"List": [
{"Mfr": "One"},
{"Mfr": "Two"}
]
}]
},
{
"T3": "Video",
"List": [{
"Prod": "Video System",
"List": [
{"Mfr": "Other"}
]
}]
}]
}]
}]
}] I did get the result I intend to get as described above. I used underscore to get the result. Following code snippet did the job for me :
var items = _.map(_.groupBy(itemList, 'Corp'), function (a) {
return _.extend(_.pick(a[0], 'Corp'), {
List: _.map(_.groupBy(a, 'T1'), function (b) {
return _.extend(_.pick(b[0], 'T1'), {
List: _.map(_.groupBy(b, 'T2'), function (c) {
return _.extend(_.pick(c[0], 'T2'), {
List: _.map(_.groupBy(c, 'T3'), function (d) {
return _.extend(_.pick(d[0], 'T3'), {
List: _.map(_.groupBy(d, 'Prod'), function (e) {
return _.extend(_.pick(e[0], 'Prod'), {
List: _.map(e, function (elem) {
return _.pick(elem, 'Mfr')
})
});
})
});
})
});
})
});
})
});
});
Now, So All I am looking for, is if someone can enhance my solution. I want to optimize both space and time for this process.
PS: In morning, I had asked a similar question requesting for the solution, and that question was marked as TOO BROAD and was put on HOLD, so I have added my solution with this question, now all I am looking for is a better solution.
谢谢
为了避免重叠语句,您可能需要定义一个 'expand keys' 列表并对其进行迭代。
用类似的东西自动提取密钥有点诱人:
expandKeys = _.keys(itemList[0]);
但由于 Javascript 不能保证对象中键的顺序,您确实应该显式定义此列表。
下面是一些示例代码。
var itemList = [
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System", "T3": "Audio", "Prod": "Audio System", "Mfr": "One"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System", "T3": "Audio", "Prod": "Audio System", "Mfr": "Two"},
{"Corp": "ABC", "T1": "HW A/V", "T2": "A/V System", "T3": "Video", "Prod": "Video System", "Mfr": "Other"}
];
var expandKeys = [ 'Corp', 'T1', 'T2', 'T3', 'Prod', 'Mfr' ];
function expandList(list, keys) {
var node, obj, root = {};
_.each(list, function(item) {
obj = root;
_.each(keys, function(key) {
obj = (obj.List = obj.List || []);
node = _.find(obj, function(i) { return i[key] == item[key]; });
if(node === undefined) {
obj.push(node = {});
node[key] = item[key];
}
obj = node;
});
});
return root.List;
}
var res = expandList(itemList, expandKeys);
console.log(res);
<script src="http://underscorejs.org/underscore-min.js"></script>