處理多維陣列時,常需根據特定鍵的值刪除對應的子陣列。本文提供一個通用函數 searchArray(),支援指定鍵名與目標值,移除所有匹配的子陣列並保持索引連續。
/**
* 從多維陣列中移除指定鍵值匹配的子陣列
* @param array $array 來源陣列 (索引陣列,值為關聯陣列)
* @param string $key 要比對的鍵名
* @param mixed $value 目標值
* @return array 過濾後的陣列 (重新索引)
*/
function searchArray(array $array, $key, $value) {
foreach ($array as $idx => $item) {
if (is_array($item) && isset($item[$key]) && $item[$key] == $value) {
unset($array[$idx]);
}
}
return array_values($array); // 重置數字索引
}
// 測試資料
$data = [
['id' => 1, 'name' => 'Alice'],
['id' => 2, 'name' => 'Bob'],
['id' => 3, 'name' => 'Bob'],
['id' => 4, 'name' => 'Charlie'],
];
// 刪除所有 name 為 Bob 的項目
$result = searchArray($data, 'name', 'Bob');
print_r($result);
/* 輸出:
Array
(
[0] => Array ( [id] => 1 [name] => Alice )
[1] => Array ( [id] => 4 [name] => Charlie )
)
*/
function filterArrayRecursive(array $array, callable $predicate) {
$result = [];
foreach ($array as $item) {
if (is_array($item)) {
// 如果是關聯陣列 (有字串鍵) 視為葉子節點判斷
if (array_keys($item) !== range(0, count($item) - 1)) {
if (!$predicate($item)) {
$result[] = $item;
}
} else {
// 索引陣列遞迴處理
$filtered = filterArrayRecursive($item, $predicate);
if (!empty($filtered)) $result[] = $filtered;
}
}
}
return $result;
}
// 使用範例:刪除 id > 2 且 name 包含 'o' 的項目
$data = [
['id' => 1, 'name' => 'Alice'],
['id' => 2, 'name' => 'Bob'],
['id' => 3, 'name' => 'Bob'],
['id' => 4, 'name' => 'Charlie'],
];
$filtered = filterArrayRecursive($data, function($item) {
return $item['id'] > 2 && strpos($item['name'], 'o') !== false;
});
print_r($filtered); // 保留 id 1, 2, 4
array_filter() 搭配參考傳遞減少複製開銷。collect($data)->reject(fn($i) => $i['name'] === 'Bob')->values()->all() 鏈式語法更優雅。==,若需型別嚴格請改 ===。