I am trying to convert array of objects to object of array using javascript.
Here is the code
const data = [{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "16",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma12313"
},
{
yearMonthKey: "201908",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}]
let programs = {};
I want to use programs object to make an object out of it like this below.
{
201907: {
15: [{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma123132"
}],
16: [{
yearMonthKey: "201907",
dayKey: "16",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}]
},
201908: {
15: [{
yearMonthKey: "201908",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}]
}
}
I try to solve it using map in array method.
data.map(item => {
programs[item.yearMonthKey] : {
programs[item.dayKey] : [{
}]
}
})
but it is bit challenging to sort objects as a value of same dayKey key inside of an array and put those inside of same yearMonthKey.
5 Answers 5
You could reduce the array. Add each yearMonthKey to the accumulator. Based on the yearMonthKey add a nested dayKey key to the acc[yearMonthKey] object and default it to an array.
const data=[{yearMonthKey:"201907",dayKey:"15",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma"},{yearMonthKey:"201907",dayKey:"15",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma"},{yearMonthKey:"201907",dayKey:"16",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma12313"},{yearMonthKey:"201908",dayKey:"15",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma"}];
const output = data.reduce((acc, o) => {
if (!acc[o.yearMonthKey])
acc[o.yearMonthKey] = {};
if (!acc[o.yearMonthKey][o.dayKey])
acc[o.yearMonthKey][o.dayKey] = [];
acc[o.yearMonthKey][o.dayKey].push(o);
return acc;
}, {})
console.log(output)
Comments
const data = [{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "16",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma12313"
},
{
yearMonthKey: "201908",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}]
let programs = {};
data.forEach(function(element) {
if (typeof programs[element.yearMonthKey] == "undefined") {
programs[element.yearMonthKey] = {};
}
if(typeof programs[element.yearMonthKey][element.dayKey] == "undefined") {
programs[element.yearMonthKey][element.dayKey] = [];
}
programs[element.yearMonthKey][element.dayKey].push(
element
);
});
console.log(programs);
Comments
Universal function for grouping with any keys
function group() {
const args = Array.from(arguments)
const data = args.shift()
const result = {}
data.forEach(elem => {
let level = result
args.forEach((groupProp, ind) => {
const groupValue = elem[groupProp]
if (groupValue in level) {
level = level[groupValue]
} else {
level = level[groupValue] = ind === args.length - 1 ? [] : {}
}
})
level.push(elem)
})
return result
}
const data = [{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "16",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma12313"
},
{
yearMonthKey: "201908",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}]
const result = group(data, 'yearMonthKey', 'dayKey')
console.log(result)
Comments
const data=[{yearMonthKey:"201907",dayKey:"15",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma"},{yearMonthKey:"201907",dayKey:"15",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma"},{yearMonthKey:"201907",dayKey:"16",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma12313"},{yearMonthKey:"201908",dayKey:"15",startDate:"2019-07-15 00:00:00+0900",title:"testProgrma"}];
const dist_yearMonthKeys = [...new Set(data.map(d => d.yearMonthKey))];
let program = {};
for (let ymk of dist_yearMonthKeys) {
const ymk_num = parseInt(ymk); // error-prone, be careful with your source data
program[ymk_num] = {};
const dist_dayKeys = [...new Set(data.filter(d => d.yearMonthKey === ymk).map(d => d.dayKey))];
for (let dk of dist_dayKeys) {
const dk_num = parseInt(dk); // error-prone
program[ymk_num][dk_num] = data.filter(d => d.dayKey === dk && d.yearMonthKey === ymk);
}
}
console.log(program);
This gives numeric keys, like you requested.
1 Comment
parseInt(ymk). Keys of an object are either a string or a Symbol. When you add program[ymk_num] it will be converted to a string.try destructuring the list and putting it back together in the format you want
const data = [{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
},
{
yearMonthKey: "201907",
dayKey: "16",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma12313"
},
{
yearMonthKey: "201908",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}]
const [1,2,3,4] = data
so now when you call variable 1 you would get
{
yearMonthKey: "201907",
dayKey: "15",
startDate: "2019-07-15 00:00:00+0900",
title: "testProgrma"
}
Now you can handle each object individually instead of in a list. As such you can basically do whatever you want with the objects
mapwhen the desired result is a key-value object