philipp
philipp

Reputation: 16515

PHP—array_merge_recursive() - no Array for same keys

$php -a
php > $data1 = ['tag' => 'div', 'classes' => [1,2,3]];
php > $data2 = ['tag' => 'section', 'classes' => [2,3,4,5,6]];
php > $result = array_merge_recursive($data1, $data2);
php > print_r($result);
Array
(
    [tag] => Array
        (
            [0] => div
            [1] => section
        )

    [classes] => Array
        (
            [0] => 1
            [1] => 2
            [2] => 3
            [3] => 2
            [4] => 3
            [5] => 4
            [6] => 5
            [7] => 6
        )

 )

So as describes in the Docs:

If the input arrays have the same string keys, then the values for these keys are merged together into an array[…]

Is there a existing function within PHP that basically does the same, but without merging the same keys into an array, so that the values are overridden and the key kept?

In this case I would like to have that result:

Array
(
    [tag] => section

    [classes] => Array
        (
            [0] => 1
            [1] => 2
            [2] => 3
            [5] => 4
            [6] => 5
            [7] => 6
        )

 )

In regards to the comment of @JustOnUnderMillions:

Yes I wonder, that is not what I would expect of such a function, I would expect a result as I am looking for.

Upvotes: 3

Views: 802

Answers (2)

Guillaume Sainthillier
Guillaume Sainthillier

Reputation: 1685

You can deal with this function (recursive and multi-arrays):

<?php

$data1 = ['tag' => 'div', 'classes' => [1,2,3], 'foo' => ['bar' => [1,2], 'bar2' => 'foo']];
$data2 = ['tag' => 'section', 'classes' => [2,3,4,5,6], 'foo' => ['bar' => [2,3], 'bar3' => 'foo']];
$data3 = ['tag' => 'section', 'classes' => [7], 'foo' => ['bar' => [5], 'bar3' => 'foo2']];


print_r(custom_array_merge($data1, $data2, $data3));

function custom_array_merge() {
    $arguments = func_get_args();
    $datas = call_user_func_array('array_merge', $arguments);
    foreach($datas as $key => $value) {
        if(is_array($value)) {
            $values = [];
            foreach($arguments as $array) {
                $values[] = isset($array[$key]) ? $array[$key] : [];
            }

            if(array_depth($value) === 1) {
                $datas[$key] = array_unique(call_user_func_array('array_merge', $values));
            }else {
                $datas[$key] = call_user_func_array('custom_array_merge', $values);
            }
        }
    }

    return $datas;
}

function array_depth(array $array) {
    $max_depth = 1;

    foreach ($array as $value) {
        if (is_array($value)) {
            $depth = array_depth($value) + 1;

            if ($depth > $max_depth) {
                $max_depth = $depth;
            }
        }
    }

    return $max_depth;
}

Upvotes: 1

JustOnUnderMillions
JustOnUnderMillions

Reputation: 3795

To get the result you need use this:

function my_array_merge_recursive($array1,$array2){
   foreach($array1 as $key=>&$val){
       if(!isset($array2[$key])){
           contiune;
       }
       if(is_array($val)){
           $val = array_unique(array_merge($val,$array2[$key]));
       } else {
           $val=$array2[$key];
       }
       unset($array2[$key]);
   }
   #if we have entries left in second array
   if(count($array2)){
       return array_merge($array1,$array2);
   }
   return $array1;
}
$data1 = ['tag' => 'div', 'classes' => [1,2,3]];
$data2 = ['tag' => 'section', 'classes' => [2,3,4,5,6]];
$result = my_array_merge_recursive($data1, $data2);
print_r($result);

This function is only for this special case.

Upvotes: 0

Related Questions