So I have this array
var mapped = [[2016, \"October\", \"Monday\", {object}], [2017, \"January\", \"Friday\", {object}], [2017, \"January\", \"Wednesday\", {obje
Not exactly what you specified, but I feel the following script outputs a format that will be most useful -- it only produces arrays at the deepest level:
const mapped = [[2016, "October", "Monday", { a: 1 }], [2017, "January", "Friday", { a: 1 }], [2017, "January", "Wednesday", { a: 1 }], [2017, "October", "Monday", { a: 1 }]];
const result = mapped.reduce( (acc, [year, month, day, object]) => {
let curr = acc[year] = acc[year] || {};
curr = curr[month] = curr[month] || {};
curr = curr[day] = curr[day] || [];
curr.push(object);
return acc;
}, {});
console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }
If you really need the wrapping arrays, you can apply an extra recursive function to the previous result:
const mapped = [[2016, "October", "Monday", { a: 1 }], [2017, "January", "Friday", { a: 1 }], [2017, "January", "Wednesday", { a: 1 }], [2017, "October", "Monday", { a: 1 }]];
const result = mapped.reduce( (acc, [year, month, day, object]) => {
let curr = acc[year] = acc[year] || {};
curr = curr[month] = curr[month] || {};
curr = curr[day] = curr[day] || [];
curr.push(object);
return acc;
}, {});
function wrapInArrays(data) {
return Array.isArray(data) ? data
: Object.entries(data).map ( ([key, value]) => {
return { [key]: wrapInArrays(value) };
});
}
const wrapped = wrapInArrays(result);
console.log(wrapped);
.as-console-wrapper { max-height: 100% !important; top: 0; }
To achieve the same exact structure you can try the strategy below. This will work upto any level of nesting and will continue to build the nested object. Please have a look at the example to see various levels of nesting which will be handled generically.
Map each element into the corresponding nested structure (Map with reduce)
Combine each element from mapped array into a single object to merge all redundant keys
Convert the final nested object into the desired array structure.
const mapped = [[2016, "October", "Monday", "Morning", {time: "10AM"}], [2017, "January", "Friday", {object: "OBJECT"}], [2017, "January", "Wednesday", {object: "OBJECT"}], [2017, "October", "Monday", {object: "OBJECT"}]];
// Map all objects to the respective nested structure
const nestedMap = mapped.map(elem => {
let reversed = [...elem.reverse()];
let firstElem = reversed.splice(0, 1)[0];
return reversed.reduce((acc, elem) => {let newAcc = {}; newAcc[elem] = [acc]; return {...newAcc}}, firstElem);
})
// Combine array to form a single object
const nestedObj = nestedMap.reduce((acc, elem) => {
let firstKey = Object.keys(elem)[0];
acc[firstKey]
?
acc[firstKey].push(elem[firstKey][0])
:
acc[firstKey] = elem[firstKey];
return acc;
}, {})
// Convert back into the array with each object as element
const nestedFinalArr = Object.keys(nestedObj).map(key => ({[key]: nestedObj[key]}))
console.log(nestedFinalArr);