0

I have two arrays:

Array 1:

[
    {
        name: 'Bob',
        traits: {
            id: 1
        }
    }, {
        name: 'Karl',
        traits: {
            id: 2
        }
    }, {
        name: 'Joseph',
        traits: {
            id: 3
        }
    }
]

Array 2:

[
    {
        name: 'Karl',
        user_id: 2,
        dog: 'Rottweiler'
    }, {
        name: 'Joseph',
        user_id: 3,
        dog: 'Poodle'
    }, {
        name: 'Bob',
        user_id: 1,
        dog: 'Puppy'
    }
]

Desired outcome:

I want to be able to merge the second array into the first array by finding what element user_id matches with id and then adding the object to array.

For example:

array 1 obj

{
    name: 'Bob',
    traits: {
        id: 1
    }
}

Since the id matches with array 2 obj user_id:

{
    name: 'Bob',
    user_id: 1,
    dog: 'Puppy'
}

Final outcome will be:

{
    name: 'Bob',
    traits: {
        name: 'Bob',
        user_id: 1,
        dog: 'Puppy'
    }
}
VLAZ
  • 26,331
  • 9
  • 49
  • 67
Juliette
  • 4,309
  • 2
  • 14
  • 31

4 Answers4

1

arr2.forEach((obj) => {
    const idx = arr1.findIndex((o) => o.traits.id === obj.user_id);
    if (idx !== -1) {
        arr1[idx] = { ...arr1[idx], traits: { ...obj } }
    }
})

console.log(arr1[0]) // { name: 'Bob', traits: { name: 'Bob', user_id: 1, dog: 'Puppy' } }
Dor Ben Itzhak
  • 285
  • 2
  • 5
0

Turn the second array into a map keyed by user_id, and then iterate the first array. Find the corresponding object in the map, and spread the matching object value into the traits property:

let arr1 = [{name: 'Bob',traits: {id: 1}},{name: 'Karl',traits: {id: 2}},{name: 'Joseph',traits: {id: 3}}];
let arr2 = [{name: 'Karl', user_id: 2,dog: 'Rottweiler'},{name: 'Joseph', user_id: 3,dog: 'Poodle'},{name: 'Bob',user_id: 1,dog: 'Puppy'}];

let map = new Map(arr2.map(item => [item.user_id, item]));

let result = arr1.map(item => {
    let traits = map.get(item.traits.id);
    return traits ? { ...item, traits} : item;
});

console.log(result);

As lookup in a map has an amortised time complexity of O(1), this is more efficient than finding the key in the array on every iteration (like with calling find).

trincot
  • 317,000
  • 35
  • 244
  • 286
0

You can easily achieve this result using map and find. Just map over the first array and find the element with obj.traits.id in the arr2. then return the desired result.

const arr1 = [
  {
    name: "Bob",
    traits: {
      id: 1,
    },
  },
  {
    name: "Karl",
    traits: {
      id: 2,
    },
  },
  {
    name: "Joseph",
    traits: {
      id: 3,
    },
  },
];

const arr2 = [
  {
    name: "Karl",
    user_id: 2,
    dog: "Rottweiler",
  },
  {
    name: "Joseph",
    user_id: 3,
    dog: "Poodle",
  },
  {
    name: "Bob",
    user_id: 1,
    dog: "Puppy",
  },
];

const result = arr1.map((obj) => {
  const { name, traits } = obj;
  const isExist = arr2.find((o) => o.user_id === traits.id);
  if (isExist) {
    return { name, traits: { ...isExist } };
  }
  return obj;
});

console.log(result);
DecPK
  • 24,537
  • 6
  • 26
  • 42
0

let a = [
    {
        name: 'Bob',
        traits: {
            id: 1
        }
    }, {
        name: 'Karl',
        traits: {
            id: 2
        }
    }, {
        name: 'Joseph',
        traits: {
            id: 3
        }
    }
    ];

    let b = [
        {
            name: 'Karl',
            user_id: 2,
            dog: 'Rottweiler'
        }, {
            name: 'Joseph',
            user_id: 3,
            dog: 'Poodle'
        }, {
            name: 'Bob',
            user_id: 1,
            dog: 'Puppy'
        }
    ];
    
    a.map(aobj =>{
    let sameIdObj = b.find( bobj => bobj.user_id === aobj.traits.id )
    sameIdObj && (aobj.traits =  sameIdObj)
    })

    console.log(a);