Reputation: 177
So I have this data:
const data = [
{
product_name: 'BMW',
year: '1982'
},
{
product_name: 'BMW',
year: '1998'
},
{
product_name: 'LandRover',
year: '1982'
},
{
product_name: 'BMW',
year: '1982'
},
{
product_name: 'LandRover',
year: '1985'
},
{
product_name: 'LandRover',
year: '1981'
}
]
Using vanilla javascript I need to filter the data into an array like this:
[
{
name: 'BMW',
data: [1982, 1998, 1982]
},
{
name: 'LandRover',
data: [1982, 1985, 1981]
}
]
Can anyone help? Not sure the best way to approach this.
Many thanks
Upvotes: 0
Views: 87
Reputation: 115242
Use Array#reduce
method with a hashmap to refer index.
// object for refering index
const ref = {};
// iterate over the object array
let res = data.reduce((arr, o) => {
// check already present in array
if (!(o.product_name in ref)) {
// if not present define the index reference
// and define object
arr[ref[o.product_name] = arr.length] = {
name: o.product_name,
data: []
};
}
// push into the data array
arr[ref[o.product_name]].data.push(o.year);
// return array reference
return arr;
// set initial value as array
}, [])
const data = [{ product_name: 'BMW', year: '1982' }, { product_name: 'BMW', year: '1998' }, { product_name: 'LandRover', year: '1982' }, { product_name: 'BMW', year: '1982' }, { product_name: 'LandRover', year: '1985' }, { product_name: 'LandRover', year: '1981' }];
const ref = {};
let res = data.reduce((arr, o) => {
if(!(o.product_name in ref)) arr[ref[o.product_name] = arr.length] = { name: o.product_name, data: [] };
arr[ref[o.product_name]].data.push(o.year);
return arr;
}, [])
console.log(res);
Upvotes: 0
Reputation: 9
You can try this function
function convert(datas) {
var hash_result = {}
datas.forEach(function(data) {
console.log(hash_result[data['product_name']])
if(hash_result[data['product_name']]) {
hash_result[data['product_name']].push(data['year'])
} else {
hash_result[data['product_name']] = [data['year']]
}
})
var result = []
Object.keys(hash_result).forEach(function(key) {
result.push({
name: key,
data: hash_result[key]
})
})
return result
}
Upvotes: 0
Reputation: 68423
Use reduce
var output = Object.values(data.reduce( function( a,b ){
a[ b.product_name ] = a[ b.product_name ] || { name : b.product_name, data: [] }; //initialize the object as { name : .., data: [] };
a[ b.product_name ].data.push( Number( b.year ) ); //push the year to data array after converting the same to a Number
return a; //return the accumulator
}, {})); //finally return the object.values
Demo
var data = [
{
product_name: 'BMW',
year: '1982'
},
{
product_name: 'BMW',
year: '1998'
},
{
product_name: 'LandRover',
year: '1982'
},
{
product_name: 'BMW',
year: '1982'
},
{
product_name: 'LandRover',
year: '1985'
},
{
product_name: 'LandRover',
year: '1981'
}
];
var output = Object.values(data.reduce(function(a, b) {
a[b.product_name] = a[b.product_name] || {
name: b.product_name,
data: []
}; //initialize the object as { name : .., data: [] };
a[b.product_name].data.push(Number(b.year)); //push the year to data array after converting the same to a Number
return a; //return the accumulator
}, {}));
console.log( output );
Upvotes: 2
Reputation: 192452
You can reduce the data to a Map, get the Map values iterator, and then spread it to an array:
const data = [{"product_name":"BMW","year":"1982"},{"product_name":"BMW","year":"1998"},{"product_name":"LandRover","year":"1982"},{"product_name":"BMW","year":"1982"},{"product_name":"LandRover","year":"1985"},{"product_name":"LandRover","year":"1981"}];
const result = [...data.reduce((m, o) => {
// if map doesn't have the product_name, init the object and add to map
m.has(o.product_name) || m.set(o.product_name, {
name: o.product_name,
data: []
});
// get the product object, and add the year
m.get(o.product_name).data.push(o.year);
return m;
}, new Map()).values()]; // get the map values, and spread to an array
console.log(result);
Upvotes: 4