array_filter($arr) 默认按 empty() 规则过滤 null、""、0、0.0、false、[]、"0";需保留 0 和 false 时须传回调函数严格判断;多维数组需自定义递归函数;键名乱序可用 array_values() 重置。

array_filter() 是 PHP 中处理数组空值最直接、最常用的方式,但它默认行为容易误删合法值(比如 0、false、"0"),所以不能无脑调用。
默认不传回调时会删掉哪些值?
当只写 array_filter($arr) 且不传第二个参数时,PHP 实际是按 empty() 规则判断的。以下值会被过滤掉:
null- 空字符串
"" - 整数
0和浮点数0.0 - 布尔值
false - 空数组
[] - 字符串
"0"(注意:这个常被忽略)
如果你的数据里有 ID 字段为 0,或状态字段为 false(表示“关闭”),直接这么用就会出错。
想只删 null 和 "",保留 0 和 false 怎么办?
必须显式传入回调函数,并用严格比较:
立即学习“PHP免费学习笔记(深入)”;
$filtered = array_filter($arr, function($v) {
return $v !== null && $v !== '';
});
如果还要排除只含空白字符的字符串(如 " "、"\t\n"),加 trim():
$filtered = array_filter($arr, function($v) {
return $v !== null && !is_string($v) || (is_string($v) && trim($v) !== '');
});
注意:这里要先判断是否为字符串,否则对数字或布尔值调用 trim() 会触发警告。
多维数组怎么深层过滤?
array_filter() 本身不递归,但可以自己封装一个递归函数:
function array_filter_recursive($arr) {
foreach ($arr as $k => $v) {
if (is_array($v)) {
$arr[$k] = array_filter_recursive($v);
}
if ($v === null || $v === '') {
unset($arr[$k]);
}
}
return $arr;
}
这个版本只做浅层空值清理(即只清当前层级的 null/""),不会碰子数组里的 0 或 false。如果子数组也需要同样逻辑,把 unset 条件也加到递归调用后即可。
过滤完键名乱了,怎么重置索引?
array_filter() 默认保留原键名,这对关联数组是优点,但对纯索引数组可能造成问题(比如后续用 for 循环时下标不连续)。补一句 array_values() 就行:
$filtered = array_values(array_filter($arr, fn($v) => $v !== null && $v !== ''));
注意:不要写成 array_values(array_filter(...)) 后再赋值给原变量却不重命名——如果原数组是引用传递或被其他地方依赖键名,重置索引可能破坏逻辑。
真正容易被忽略的是:过滤条件必须和业务语义对齐。比如用户输入的数字字段,"0" 是有效值还是空值?前端传来的 "false" 字符串要不要转布尔再判?这些没法靠一个函数自动解决,得在回调里明确写清楚。



















