How to merge two arrays of object in PHP

Viewed 43284

I have the following two arrays of objects:

First Array: $array1

Array
(
    [0] => stdClass Object
        (
            [id] => 100
            [name] => Muhammad
        )

    [1] => stdClass Object
        (
            [id] => 102
            [name] => Ibrahim
        )

    [2] => stdClass Object
        (
            [id] => 101
            [name] => Sumayyah
        )
)

Second Array: $array2

Array
(
    [0] => stdClass Object
        (
            [id] => 100
            [name] => Muhammad
        )

    [1] => stdClass Object
        (
            [id] => 103
            [name] => Yusuf
        )
)

I want to merge these two object arrays (removing all duplicates) and sorted according to id.

Desired output:

Array
(
    [0] => stdClass Object
        (
            [id] => 100
            [name] => Muhammad
        )

    [1] => stdClass Object
        (
            [id] => 101
            [name] => Sumayyah
        )

    [2] => stdClass Object
        (
            [id] => 102
            [name] => Ibrahim
        )

    [3] => stdClass Object
        (
            [id] => 103
            [name] => Yusuf
        )
)
3 Answers

Assignments:

  1. Merge
  2. Remove Duplicates
  3. Sort by id

The good news is: Assigning temporary keys using id values does all of the hard work for you. No serializing is needed.

  • array_merge() joins the arrays together.
  • array_column() with a null 2nd parameter leaves the objects unmodified and id as the 3rd parameter assigns the temporary keys. Because arrays cannot have duplicate keys, duplicate objects are weeded out in this step.
  • Now that we have keys, ksort() avoids calling the more convoluted usort() to sort by id ascending.
  • Finally, call array_values() to re-index the resultant array (remove the temporary keys).

Code: (Demo)

$array1 = [
    (object) ['id' => 100, 'name' => 'Muhammad'],
    (object) ['id' => 102, 'name' => 'Ibrahim'],
    (object) ['id' => 101, 'name' => 'Sumayyah']
];

$array2 = [
    (object) ['id' => 100, 'name' => 'Muhammad'],
    (object) ['id' => 103, 'name' => 'Yusuf']
];

$merged_keyed = array_column(array_merge($array1,$array2), NULL, 'id');
ksort($merged_keyed);
var_export(array_values($merged_keyed));

Alternatively, you can filter one of the arrays to remove duplicates, then merge them, then sort them. sort() will effectively order the rows by the id column because the rows have equal size and id is the element in first position.

Code: (Demo)

$result = array_merge($array1, array_udiff($array2, $array1, fn($a, $b) => $a <=> $b));
sort($result);
var_export($result);

Output (from either snippet):

array (
  0 => 
  (object) array(
     'id' => 22,
     'name' => 'Ibrahim',
  ),
  1 => 
  (object) array(
     'id' => 100,
     'name' => 'Muhammad',
  ),
  2 => 
  (object) array(
     'id' => 101,
     'name' => 'Sumayyah',
  ),
  3 => 
  (object) array(
     'id' => 103,
     'name' => 'Yusuf',
  ),
)
Related