7

I want concat following two arrays by removing duplicates without assigning to third variable:

var arr1=[{id:1,name:'AB'},{id:2,name:'CD'}]; var arr2=[{id:3,name:'EF'},{id:2,name:'CD'}]; 

I want arr1 like:

[{id:1,name:'AB'},{id:2,name:'CD'},{id:3,name:'EF'}] arr1.concat(arr2); 
5
  • 1
    Use lodash union lodash.com/docs/4.17.10#union or lodash.com/docs/4.17.11#uniqWith Commented Jan 8, 2019 at 10:56
  • you can simply loop through array which has less elements & compare with the other array . push the non-existing object to the same array to avoid usage 3rd variable.. Commented Jan 8, 2019 at 11:09
  • can you help me that loop ,am tried not getting@supercool Commented Jan 8, 2019 at 11:12
  • $.each(arr1,(i,x)=>{ if($.grep(arr2,(y)=> x.id == y.id && x.name==y.name ).length < 1) arr2.push(x); }); something like this, hope if helps. you can use .filter inplace of grep in ang Commented Jan 8, 2019 at 11:53
  • I posted here an option with JSON.stringify Commented Mar 29, 2020 at 18:26

9 Answers 9

7

First merge two arrays then put array into a map with their ids. Then create array from map values.

var arr1=[{id:1,name:'AB'},{id:2,name:'CD'}]; var arr2=[{id:3,name:'EF'},{id:2,name:'CD'}]; arr1 = arr1.concat(arr2) // merge two arrays let foo = new Map(); for(const tag of arr1) { foo.set(tag.id, tag); } let final = [...foo.values()] console.log(final)

Sign up to request clarification or add additional context in comments.

Comments

6

Can use Array reduce and findIndex to achieve what you want.

var arr1=[{id:1,name:'AB'},{id:2,name:'CD'}]; var arr2=[{id:3,name:'EF'},{id:2,name:'CD'}]; // loop over arr2, add the elements of array2 if it doesn't exist in array1 var newArr = arr2.reduce((acc, eachArr2Elem) => { if (arr1.findIndex((eachArr1Elem) => eachArr1Elem.id === eachArr2Elem.id && eachArr1Elem.name === eachArr2Elem.name) === -1) { acc.push(eachArr2Elem) } return acc }, [...arr1]); // initialize the new Array with the contents of array1 console.log(newArr)

5 Comments

is it possible without assigning to third variable
@madhuGoud: You also mean the variables in the callBacks? I guess No (Not in plain Javascript), Here the elements are Objects, there is no simple way to concat them and remove duplicates
is it possible in typescript
@madhuGoud: TypeScript is just a superset of Javascript, it is not a library. I am not clear with what you mean by the third variable. Do you want to modify any of the existing arr1 or arr2 with new array? Remember, something like: arr1.concat(arr2); is also a new reference, its just that you are not assigning it to a variable
@madhuGoud Check my solution if you want, I solved this with using map. Since your arrays have objects in it, it's not that simple. If your arrays were not objects, you could use Set to achieve unique array easily.
1

using the spread operator you can flatten any amount of arrays passed to the combineAndDeDup method, i have also split out some logic methods for (hopefully) more readable code. i hope this helps.

const arr1 = [{id:1,name:'AB'}, {id:2,name:'CD'}] const arr2 = [{id:3,name:'EF'}, {id:2,name:'CD'}] const flatten = a => [].concat.apply([], a) const noDuplicateProps = (a, b) => Object.keys(a).some(k => a[k] === b[k]) const combineAndDeDup = (...arrs) => { return flatten(arrs).reduce((acc, item) => { const uniqueItem = acc.findIndex(i => noDuplicateProps(i, item)) === -1 if (uniqueItem) return acc.concat([ item ]) return acc }, []) } const deDuped = combineAndDeDup(arr1, arr2) const megaDeDuped = combineAndDeDup(arr1, arr2, arr1, arr1, arr2, arr1) console.log(deDuped) console.log(megaDeDuped)

1 Comment

what to add if in case one array is empty than the result should be empty as well?
1

If you like clean ES6 try this:
Happy code :)

function arrayWithNoDuplicates(array, field) { const arrayWithoutNoDuplicates = array.filter((value, index, self) => index === self.findIndex((t) => ( t[field] === value[field] )) ) return arrayWithoutNoDuplicates } const arr1 = [{id:1,name:'AB'}, {id:2,name:'CD'}] const arr2 = [{id:3,name:'EF'}, {id:2,name:'CD'}] // The first param is the two merged arrays and the second the field you // to filter by console.log(arrayWithNoDuplicates([...arr1, ...arr2], 'id'))

Comments

0

By using lodash _.uniqWith(array, [comparator])

var objects = [{ 'x': 1, 'y': 2 }, { 'x': 2, 'y': 1 }, { 'x': 1, 'y': 2 }]; _.uniqWith(objects, _.isEqual); // => [{ 'x': 1, 'y': 2 }, { 'x': 2, 'y': 1 }] 

Comments

0
 var arr1 = [{ id: 1, name: 'AB' }, { id: 2, name: 'CD' }]; var arr2 = [{ id: 3, name: 'EF' }, { id: 3, name: 'XX' }]; arr1.forEach(element => { arr2.forEach((el, idx) => { if (element.id === el.id || element.name === el.name) { delete arr2[idx] } }); }); let data = arr1.concat(arr2) // or arr1 = arr1.concat(arr2) // then your arr1 contains your unique array 

data variable contains your unique array

Comments

0

Here is the one liner that compares by id.

let result = arr1.concat( arr2.filter( i2 => !arr1.find( i1 => i1.id == i2.id ) ) ); 

I have modified elements to show what happens for different objects with the same id. Swap arr1 with arr2 for which array you want to keep your preferred components. There seems to be no simple way to compare objects in JavaScript, you may use JSON.stringify but that depends on elements order. You can try it out at https://playcode.io/new/ :

var arr1=[{id:1,name:'AB'},{id:2,name:'CD'}]; var arr2=[{id:3,name:'EF'},{id:2,name:'GH'}]; let result; result = arr1.concat( arr2.filter( i2 => !arr1.find( i1 => i1.id == i2.id ) ) ); console.log('RESULT: ' + JSON.stringify(result)); result = arr1.concat( arr2.filter( i2 => !arr1.find( i1 => { console.log('I1: ' + JSON.stringify(i1) + ' I2: ' + JSON.stringify(i2)); return i1.id == i2.id;} ) ) ); console.log('RESULT: ' + JSON.stringify(result)); result = arr2.concat( arr1.filter( i1 => !arr2.find( i2 => { console.log('I1: ' + JSON.stringify(i1) + ' I2: ' + JSON.stringify(i2)); return i1.id == i2.id;} ) ) ); console.log('RESULT: ' + JSON.stringify(result)); 

Comments

0

Both lodash function unionBy and unionWith can solve your problem.

If your objects has unique key, unionBy is the most elegant way to handle it.

var arr1 = [{id:1,name:'AB'},{id:2,name:'CD'}]; var arr2 = [{id:3,name:'EF'},{id:2,name:'CD'}]; var mergedWithoutDups = _.unionBy(arr1, arr2. 'id') 

If your object has no unique key, use unionWith and isEqual instead. This will take deep comparison on all objects to remove duplicate.

var arr1 = [{id:1,name:'AB'},{id:2,name:'CD'}]; var arr2 = [{id:3,name:'EF'},{id:2,name:'CD'}]; var mergedWithoutDups = _.unionWith(arr1, arr2. _.isEqual) 

Comments

0

Here I use splice to remove the first element in arr2 and concat it to arr1.

let arr1=[{id:1,name:'AB'},{id:2,name:'CD'}]; let arr2=[{id:3,name:'EF'},{id:2,name:'CD'}]; console.log(arr1.concat(arr2.splice(0,1))); 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.