我有以下两个数组:
$a = [
['code' => '123', 'name' => 'ABC',],
['code' => '456', 'name' => 'XYZ',],
];
$b = [
['code' => '123', 'name' => 'ABC', 'price' => '34'],
['code' => '456', 'name' => 'PQR', 'price' => '56'],
['code' => '456', 'name' => 'XYZ', 'price' => '90'],
];
我想创建第三个数组,其中代码和名称的组合匹配,如下所示:
$c = [
['code' => '123', 'name' => 'ABC', 'price' => '34'],
['code' => '456', 'name' => 'XYZ', 'price' => '90'],
]
我不想保留
$b
的第二行,因为该行中的代码和名称的组合与数组中的行不匹配 $a
您的数据结构没有构建得很好,无法满足所需的比较。如果两个数组都有“复合键”而不是索引,那就更容易了。我的意思是,如果数组中的行看起来像
'123_ABC' => ['code' => '123', 'name' => 'ABC',]
那么进行直接基于键的比较将是一件轻而易举的事。
使用您拥有的资源,并为了减少数组上的总迭代次数,我建议在找到匹配项后立即在内部循环中进行早期中断的嵌套循环。
代码:(演示)
$whiteList = [
['code' => '123', 'name' => 'ABC',],
['code' => '456', 'name' => 'XYZ',],
];
$pricedList = [
['code' => '123', 'name' => 'ABC', 'price' => '34'],
['code' => '456', 'name' => 'PQR', 'price' => '56'],
['code' => '456', 'name' => 'XYZ', 'price' => '90'],
['code' => '456', 'name' => 'GHI', 'price' => '70'],
];
$result = [];
foreach ($pricedList as $pricedRow) {
foreach ($whiteList as $whiteRow) {
if ($whiteRow['code'] === $pricedRow['code'] && $whiteRow['name'] === $pricedRow['name']) {
$result[] = $pricedRow;
continue 2; // no reason to keep iterating inner loop after match is found
}
}
}
var_export($result);
或者更优雅地,对白名单数组的每一行使用
array_intersect_assoc()
。 (演示)
$result = [];
foreach ($pricedList as $pricedRow) {
foreach ($whiteList as $whiteRow) {
if ($whiteRow === array_intersect_assoc($whiteRow, $pricedRow)) {
$result[] = $pricedRow;
continue 2; // no reason to keep iterating inner loop after match is found
}
}
}
var_export($result);
输出(来自任一片段):
array (
0 =>
array (
'code' => '123',
'name' => 'ABC',
'price' => '34',
),
1 =>
array (
'code' => '456',
'name' => 'XYZ',
'price' => '90',
),
)
通过在
array_uintersect()
内部进行全行比较之前无条件清除潜在价格元素,您可以通过不包含价格的数组来过滤包含价格数据的数组。
代码:(演示)
var_export(
array_uintersect(
$pricedList,
$whiteList,
function($a, $b) {
unset($a['price'], $b['price']);
return $a <=> $b;
}
)
);