name
. number
array for each object get combined into the one object for that name number
array. The elements in the number array should appear in the same order as they appear in the original array.
var arrT = [ {name : "x.com", number :["123-456-789"]}, {name : "x.com", number :["452-123-789"]},{name : "y.com", number :["123-456-000"]}, {name : "x.com", number :["123-456-789"]}, {name : "y.com", number :["123-456-000"]}, {name : "b.com", number :["178-456-000"]} ] output should be:[ {name : "x.com", number : ["123-456-789", "452-123-789"]}, //notice: 123-456-789 didn't appear twice {name : "y.com", number : ["123-456-000"]}, {name : "b.com", number :["178-456-000"]} ]
I was able to find out how many times an object with the same name occurred
var occurrences = nArr.reduce(function(acc, curr,i){
if(typeof acc[curr.name] == "undefined"){
acc[curr.name] = 1;
}else{
acc[curr.name] += 1
}
return acc;
}, {});
console.log(occurrences)
var moreThanOne = [];
for(var key in occurrences){
if(occurrences[key] > 1){
moreThanOne.push(key);
}
}
console.log("moreThanOne", moreThanOne)
but then it got complicated because I didn't know how to remove the duplicates and leave one and combine the number
array
Not sure if you have some constraints but that's how I'd do it.
Loop over all of your object and put them into an object. The key of the object will be the name. Check if the object exists, if it doesn't add it and replace the number
by [number]
, if the object already exists, simply add the number with push
.
Once you looped over all your objects, convert that object to a list and that's it.
function groupByName(accum, obj) {
if (accum[obj.name]) {
// add all numbers! don't check for uniqueness yet
accum[obj.name].number = accum[obj.name].concat(obj.number)
} else {
accum[obj.name] = obj
obj.number = [obj.number]
}
return accum
}
function removeDuplicates(accum, value) {
if (accum.length == 0 && accum[accum.length - 1] != value) {
accum.push(value)
}
return accum
}
function toList(context) {
return function (key) {
var obj = context[key]
obj.number.sort()
obj.number = obj.number.reduce(removeDuplicates, [])
return obj
}
}
objs = arrT.reduce(groupByName, {})
output = Object.keys(objs).map(toList(objs))
Note that I'm ediding the first object so if there is no use for those objects anywhere else, that's fine... if not, you should copy in the reduce function instead of modifying and existing object.
If you only want to keep the unique numbers you just have to check if the numbers are already in.
This example creates a new object first, checks if the the name exists already, when it doesn't exist, it adds it as a completely new reference (including the number array, so your original source remains the same) and if it does exist, it will loop through the number array to see which ones should be added still.
var arrT = [{ name: "x.com", number: ["123-456-789"] }, { name: "x.com", number: ["452-123-789"] }, { name: "y.com", number: ["123-456-000"] }, { name: "x.com", number: ["123-456-789"] }, { name: "y.com", number: ["123-456-000"] }, { name: "b.com", number: ["178-456-000"] }]; var reduced = arrT.reduce((nextState, item) => { var key = item.name, o; if (!(o = nextState[key])) { // clones the item, and the number array nextState[key] = { ...item, number: [...item.number] }; } else { item.number.forEach(number => o.number.indexOf(number) === -1 && o.number.push(number)); } return nextState; }, {}); console.log(arrT); console.log(Object.keys(reduced).map(key => reduced[key]));
Another (ES6) version for the mix: with a Map and Sets
let arrT = [{name : "x.com", number :["123-456-789"]}, {name : "x.com", number :["452-123-789"]},{name : "y.com", number :["123-456-000"]}, {name : "x.com", number :["123-456-789"]}, {name : "y.com", number :["123-456-000"]}, {name : "b.com", number :["178-456-000"]} ]; let res = [...arrT.reduce((m,o) => { let set = m.get(o.name); if(!set) m.set(o.name, set = new Set()); for(let n of o.number) set.add(n); return m; }, new Map())] .map(([na,[...nrs]])=>({name:na,number:nrs})); console.log(res);
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.