Sam11
Sam11

Reputation: 73

PHP - Filtering an array to delete the values with non-similar keys from sub-arrays

I have an array like below. This is coming from a centralised database and I have no way of knowing beforehand what the actual array will contain. I want to compare the sub-arrays on keys and that is why want to delete the keys which are not present is all sub-arrays.

Array (
    [0] => Array
        (
            [a] => 
            [b] => 8
            [c] => 1
            [d] => taille-8
            [e] => 
            [k] => taill
        )

    [1] => Array
        (
            [a] => 
            [b] => 7
            [c] => 2
            [d] => taille-7
            [f] =>
            [k] => tafefef
        )

    [2] => Array
        (
            [a] => ce
            [b] => 34
            [c] => 2
            [d] => taille-34
            [g] => dee
            [k] => tacefef
        ) );

I want to delete the keys which are not repeating in all sub-arrays. In the above example they are 'e', 'f' and 'g'. This needs to happen dynamically.

Array (
    [0] => Array
        (
            [a] => 
            [b] => 8
            [c] => 1
            [d] => taille-8
            [k] => taill
        )

    [1] => Array
        (
            [a] => 
            [b] => 7
            [c] => 2
            [d] => taille-7
            [k] => tafefef
        )

    [2] => Array
        (
            [a] => ce
            [b] => 34
            [c] => 2
            [d] => taille-34
            [k] => tacefef            
        ) );

Any suggestion is appreciated.

Upvotes: 3

Views: 65

Answers (2)

Martin Cook
Martin Cook

Reputation: 749

You can use argument unpacking. If your array is stored in $a, then the following should work:

// create an array with only the keys that are common to all subarrays
$new = array_intersect_key(...$a);

// prune original array
foreach ($a as &$arr) {
    $arr = array_intersect_key($new, $arr);
}

Upvotes: 3

Andreas
Andreas

Reputation: 23958

You can splice the array and loop the rest.
In the loop I overwrite the $new with whatever is the same in each iteration.
The end should be what is matching throughout the full array.

Then we need to use the new and as a template to remove the other items in the array, so we loop again and intersect again but overwrite $arr this time.

$arr =[['a' => 1, 'b' => 2, 'c' => 3],
       ['a' => 1, 'c' => 3],
       ['c' => 3]];

$new = $arr[0];

foreach($arr as $sub){
    $new = array_intersect_key($new, $sub);
}
foreach($arr as &$sub){
    $sub =array_intersect_key($sub, $new);
}
unset($sub);
Var_dump($arr);

Output

array(3) {
  [0]=>
  array(1) {
    ["c"]=>
    int(3)
  }
  [1]=>
  array(1) {
    ["c"]=>
    int(3)
  }
  [2]=>
  &array(1) {
    ["c"]=>
    int(3)
  }
}

https://3v4l.org/oM3M1l

Upvotes: 0

Related Questions