Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Array diff of specific key within multi-dimensional array

I have two arrays of products, both formatted exactly the same, like so:

$products = array(
    [0] => array(
        ['product_id'] => 33
        ['variation_id'] => 0
        ['product_price'] => 500.00
    ),
    [1] => array(
        ['product_id'] => 48
        ['variation_id'] => 0
        ['product_price'] => 600.00
    ),
)

I would like to be able to return a list of only those products not found in the second array, based on the product ID.

I only care about those NOT found in the second array, not additional ones added to the first, so array_diff won't seem to do the trick.

like image 572
Ian McIntyre Silber Avatar asked Aug 17 '10 18:08

Ian McIntyre Silber


2 Answers

I suspect you want something like array_udiff. This lets you specify how to compare the two arrays, using a callback function. You just create a callback that compares based on product id's.

I think this satisfies what you want because the array_diff family of functions only compare the first array to the rest, it does not return elements that array2 (or 3, or 4) have that array1 does not.

<?php
$products = array(
    0 => array(
        'product_id' => 33,
        'variation_id' => 0,
        'product_price' => 500.00
    ),
    1 => array(
        'product_id' => 48,
        'variation_id' => 0,
        'product_price' => 600.00
    )
);

$products2 = array(
    1 => array(
        'product_id' => 48,
        'variation_id' => 0,
        'product_price' => 600.00
    ),
    2 => array(
        'product_id' => 49,
        'variation_id' => 0,
        'product_price' => 600.00
    )
);

function compare_ids($a, $b)
{
  return $b['product_id'] - $a['product_id'];
}

var_dump(array_udiff($products, $products2, "compare_ids"));
?>

Outputs:

array(1) {
  [0]=>
  array(3) {
    ["product_id"]=>
    int(33)
    ["variation_id"]=>
    int(0)
    ["product_price"]=>
    float(500)
  }
}
like image 180
Brandon Horsley Avatar answered Nov 03 '22 01:11

Brandon Horsley


A simple foreach loop should be enough:

<?php
$products = array(
    0 => array(
        'product_id' => 33,
        'variation_id' => 0,
        'product_price' => 500.00
    ),
    1 => array(
        'product_id' => 48,
        'variation_id' => 0,
        'product_price' => 600.00
    )
);

$products2 = array(
    1 => array(
        'product_id' => 48,
        'variation_id' => 0,
        'product_price' => 600.00
    ),
    2 => array(
        'product_id' => 49,
        'variation_id' => 0,
        'product_price' => 600.00
    )
);

$diff = array();

// Loop through all elements of the first array
foreach($products2 as $value)
{
  // Loop through all elements of the second loop
  // If any matches to the current element are found,
  // they skip that element
  foreach($products as $value2)
  {
    if($value['product_id'] == $value2['product_id'])
    continue 2;
  }
  // If no matches were found, append it to $diff
  $diff[] = $value;
}

The $diff array would then only hold the following value:

array (
  0 => 
  array (
    'product_id' => 49,
    'variation_id' => 0,
    'product_price' => 600,
  ),
)

Hope this helped!

like image 41
Frxstrem Avatar answered Nov 02 '22 23:11

Frxstrem