132

A fairly simple question. What's the difference between:

$merged = array_merge($array1, $array2);

and

$merged = $array1 + $array2;

?

The Pixel Developer
  • 13,282
  • 10
  • 43
  • 60

9 Answers9

102

Here's a simple illustrative test:

$ar1 = [
   0  => '1-0',
  'a' => '1-a',
  'b' => '1-b'
];


$ar2 = [
   0  => '2-0',
   1  => '2-1',
  'b' => '2-b',
  'c' => '2-c'
];

print_r($ar1+$ar2);

print_r(array_merge($ar1,$ar2));

with the result:

Array
(
  [0] => 1-0
  [a] => 1-a
  [b] => 1-b
  [1] => 2-1
  [c] => 2-c
)
Array
(
  [0] => 1-0
  [a] => 1-a
  [b] => 2-b
  [1] => 2-0
  [2] => 2-1
  [c] => 2-c
)

Notice that duplicate non-numeric keys will take the first value using the union operator but the later one using the array_merge.

For numeric keys, the first value will be used with the union operator whereas the all the values will be used with the array_merge, just reindexed.

I generally use union operator for associative arrays and array_merge for numeric. Of course, you can just as well use the array_merge for associative, just that the later values overwrite earlier ones.

simhumileco
  • 31,877
  • 16
  • 137
  • 115
Yehosef
  • 17,987
  • 7
  • 35
  • 56
78

The difference is:

The + operator takes the union of the two arrays, whereas the array_merge function takes the union BUT the duplicate keys are overwritten.

Joe DF
  • 5,438
  • 6
  • 41
  • 63
Mike Lewis
  • 63,433
  • 20
  • 141
  • 111
  • So, what's the difference between these 2: [array_merge](http://codepad.org/6QdQh908), [plus sign](http://codepad.org/mu0aF3tN) (although I had to switch around the arrays)? – Joseph Silber Dec 06 '11 at 20:13
  • 17
    A word of caution for beginners here, the result of the operation in both cases is **null** if any one of the arrays is **null**. Some might not care about this assuming since it is a union operation, the result will be the proper (not-null) array if one of them is **null**. But, that holds true if one of the arrays is an empty array. So, as a good practice, I think, we should initialize the input arrays as empty arrays. What do you guys say? – Sandeepan Nath Jul 13 '12 at 06:58
  • 7
    If there are duplicate keys, "taking the union" will always _have_ to get rid of one of them. The difference is in which one. – alexis Mar 11 '16 at 09:19
  • 11
    Sorry, this answer is confusing, wrong, and incomplete. :-o See @alexis's comment regarding the confusing bit (although his is also just half of the truth regarding the OP). 2. See [Yehosef's answer](https://stackoverflow.com/a/23930891/1479945) about what `array_merge` *actually* does... 3. And see [BoltClock's answer](https://stackoverflow.com/a/5394212/1479945) about another crucial difference not mentioned here: `array_merge` resets numeric keys, unlike `+`. – Sz. Sep 20 '18 at 23:31
  • 2
    not specific at all. not helpful. does not highlight the difference. too high level of an explanation. – ahnbizcad Mar 01 '19 at 18:53
  • 1
    array_merge() causes all numeric keys found in the input arrays to be reindexed in the resultant array. The union operator + does not cause a reindex – Alma Z Sep 11 '20 at 05:30
  • 1
    `The + operator returns the right-hand array appended to the left-hand array; for keys that exist in both arrays, the elements from the left-hand array will be used, and the matching elements from the right-hand array will be ignored` – Alex78191 Nov 29 '21 at 10:39
62

array_merge vs plus

Source: https://softonsofa.com/php-array_merge-vs-array_replace-vs-plus-aka-union/

Stop using array_merge($defaults, $options):

function foo(array $options)
{
   $options += ['foo' => 'bar'];

   // ...
}

Note: array_replace function exists since PHP5.3.

luchaninov
  • 6,792
  • 6
  • 60
  • 75
  • 2
    why should we stop using array_merge($default, $options):? because it disallows non-indexed keys? – ahnbizcad Mar 02 '19 at 01:19
  • but the answer is really didactic +1 – Soner from The Ottoman Empire Jun 30 '19 at 16:38
  • @ahnbizcad In the case of associative keys, which is what you’d use for defaults & options, you’ll notice that all three operations have the risk adding new elements to the first array. You normally wouldn’t want to add additional elements in this context. – Manngo Oct 20 '21 at 21:31
  • This is the best answer. I come back here and refer to it all the time. – Garrett W. Feb 16 '22 at 23:06
  • @ahnbizcad from the [source](https://p.softonsofa.com/php-array_merge-vs-array_replace-vs-plus-aka-union/) he provided: `That being said, we could think of the + operator as kinda redundant, since the same can be achieved with array_replace function. However, there are cases, where it comes in handy: say you have an $options array being passed to a function/method, and there are also defaults to be used as fallback:` – n0099 Dec 26 '22 at 01:54
59

array_merge() causes all numeric keys found in the input arrays to be reindexed in the resultant array. The union operator + does not cause a reindex.

BoltClock
  • 700,868
  • 160
  • 1,392
  • 1,356
24

The + sign only takes the value from the first occurence of an array key.
array_merge takes the value from the last occurrence of an array key.

Example:

    $first = ['a'=>'one',
            'b'=>'two',
            'c'=>'three'];
                    
    $second = ['a'=>'fourth',
            'b'=>'fifth',
            'c'=>'sixth',
            '3'=>'number three'];
                    
    $merged = $first + $second;
    echo "<pre> plus sign merge\n";
    var_dump($merged);
    
    $merged = array_merge($first,$second);
    echo "\n array_merge function merge\n";
    var_dump($merged);

This outputs:

plus sign merge
array(4) {
["a"]=>
string(3) "one"
["b"]=>
string(3) "two"
["c"]=>
string(5) "three"
[3]=>
string(12) "number three"
}

array_merge function merge
array(4) {
["a"]=>
string(6) "fourth"
["b"]=>
string(5) "fifth"
["c"]=>
string(5) "sixth"
[0]=>
string(12) "number three"
}

Interesting to note in this is that the array_merge actally erases the '3' index of number three even though it's a string, because it's a number.

So take care when merging with array_merge arrays with numerical indexes. They might lose their keys. if they are important to you precede them with a string.

Instead of '3' => 'three' use something like '_3' => 'three'


Also if you use numerical indexes it's important to note that if you add two array, it only looks at the numerical index and takes the value from the "first" array that has an array key with that value.

Array merge will merge the arrays together, ignoring similar keys and values.

So depending on the "type" of array indexes, numerical or string, the results will vary.

$arr = ['foo', 'bar', 'baz'];
$arr2 = ['xfoo', 'xbar', 'baz'];
$arr3 = $arr2 + $arr;
$arr4 = array_merge($arr, $arr2);
var_dump($arr3);

which gives the output:

array(3) {
  [0]=>
  string(4) "xfoo"
  [1]=>
  string(4) "xbar"
  [2]=>
  string(3) "baz"
}
array(6) {
  [0]=>
  string(3) "foo"
  [1]=>
  string(3) "bar"
  [2]=>
  string(3) "baz"
  [3]=>
  string(4) "xfoo"
  [4]=>
  string(4) "xbar"
  [5]=>
  string(3) "baz"
}

var_dump($arr4);

Tschallacka
  • 27,901
  • 14
  • 88
  • 133
6

I believe array_merge overwrites duplicate non_numeric keys while $array1 + $array2 does not.

klennepette
  • 3,176
  • 22
  • 23
4

Yet another example (arrays without explicit keys; it's obvious regarding to how the operator + and array_merge work, but "obvious" things are simpler when seen ;))

$a = array('apple');
$b = array('orange', 'lemon');

echo '$a + $b = ';             print_r($a + $b);
echo 'array_merge($a, $b) = '; print_r(array_merge($a, $b));

will give:

$a + $b = Array
(
    [0] => apple
    [1] => lemon
)
array_merge($a, $b) = Array
(
    [0] => apple
    [1] => orange
    [2] => lemon
)
jacek.ciach
  • 904
  • 11
  • 20
1

Please pay attention for another difference: the union (+) won't overwrite non-empty value with empty value (considering a same key), whereas array_merge will:

$a = array('foo' => 'bar');
$b = array('foo' => ''); // or false or 0

print_r($a+$b);
print_r(array_merge($a, $b);

Outputs :

Array
(
    [foo] => bar
)
Array
(
    [foo] => 0
)
ZalemCitizen
  • 474
  • 7
  • 13
0

So apparently if you change the order both union and merge will do the same thing

$a = array('foo' => 'bar', 'x' => 'fromA');
$b = array('foo' => null, 'x' => 'fromB');

echo '$a+$b: ';
var_dump($a+$b);

echo '$b+$a: ';
var_dump($b+$a);

echo 'array_merge($a, $b): ';
var_dump(array_merge($a, $b));

echo 'array_merge($b, $a): ';
var_dump(array_merge($b, $a));

Outputs :

$a+$b: array(2) {
  ["foo"]=>
  string(3) "bar"
  ["x"]=>
  string(5) "fromA"
}
$b+$a: array(2) {
  ["foo"]=>
  NULL
  ["x"]=>
  string(5) "fromB"
}
array_merge($a, $b): array(2) {
  ["foo"]=>
  NULL
  ["x"]=>
  string(5) "fromB"
}
array_merge($b, $a): array(2) {
  ["foo"]=>
  string(3) "bar"
  ["x"]=>
  string(5) "fromA"
}

Keep in mind the order of the arrays.