PHP 面试题:isset、empty、is_null 到底有什么区别

在 PHP 面试中,isset()empty()is_null() 是一组出镜率极高、却极容易被混淆的函数。很多候选人在笔试时能写出它们的定义,但一旦面试官追问“未定义变量传入会怎样”“0 和空字符串算不算空”“为什么 empty() 里不能放函数返回值”,就开始支支吾吾。

这篇文章从面试实战角度出发,把这三个函数的区别、底层行为、常见陷阱和答题思路一次讲清楚。

一、先看定义:三个函数各自在问什么

理解它们的关键,是把每个函数还原成一个“问题”:

  • isset($var):这个变量存在,并且它的值不是 null,对吗?
  • empty($var):这个变量的值是“假”的,对吗?
  • is_null($var):这个变量的值恰好等于 null,对吗?

注意措辞的差别:isset() 关心的是“存在且非 null”,empty() 关心的是“是否为假值”,is_null() 只关心“是不是 null”。三者判断的维度并不在同一个层面上,这正是混淆的根源。

二、isset 的行为细节

isset() 是语言结构(language construct),不是普通函数,因此它不能通过变量函数的方式调用,也不能接收函数返回值。

它的判断逻辑是:

$var = null;
var_dump(isset($var)); // false

$var = 0;
var_dump(isset($var)); // true

$var = '';
var_dump(isset($var)); // true

var_dump(isset($undefined)); // false,且不报 Notice

关键点有三个:

  1. 未定义变量返回 false,且不产生警告。这是它和直接读取变量最大的区别,也是它常被用来做“安全探测”的原因。
  2. 值为 null 时返回 false,哪怕变量确实已经被定义。
  3. 可以一次传多个参数isset($a, $b) 等价于 isset($a) && isset($b),全部存在且非 null 才返回 true。

三、empty 的行为细节

empty() 同样是语言结构。它的判断标准是:值在布尔上下文中为 false。也就是说,以下这些值都会让 empty() 返回 true:

  • ""(空字符串)
  • 0(整数零)
  • 0.0(浮点零)
  • "0"(字符串零,这是最容易踩坑的一个)
  • null
  • false
  • [](空数组)
  • 未定义的变量
var_dump(empty($undefined)); // true,同样不报 Notice
var_dump(empty(0));          // true
var_dump(empty('0'));        // true —— 注意!
var_dump(empty('0.0'));      // false
var_dump(empty([]));         // true
var_dump(empty(new stdClass)); // false,对象永远非空

这里最需要向面试官强调的一点是:empty('0') 返回 true。在表单处理中,用户输入 "0" 是合法值,但用 empty() 判断会被当成“没填”,这是生产环境里的经典 bug。

另外,empty() 只接受一个参数,且不能直接传入函数返回值(PHP 5.5 之前会报错,PHP 5.5+ 支持任意表达式,但传函数调用在部分老版本仍是坑)。面试时如果被问到版本差异,可以补一句:“PHP 5.5 之后 empty() 开始支持任意表达式,之前只能传变量。”

四、is_null 的行为细节

is_null() 是一个真正的函数,因此它可以接收函数返回值、可以嵌套调用,行为也最“单纯”:只有当值严格等于 null 时才返回 true。

var_dump(is_null(null));   // true
var_dump(is_null(0));      // false
var_dump(is_null(''));     // false
var_dump(is_null(false));  // false
var_dump(is_null($undefined)); // true,但会产生 Notice

注意最后一行:传入未定义变量时,is_null() 会触发 Undefined variable 警告(因为参数需要先求值),而 isset()empty() 不会。这是三者之间一个非常关键的差异,也是面试官爱问的点。

五、一张表看清全部差异

表达式 isset() empty() is_null()
$x = null false true true
$x = '' true true false
$x = '0' true true false
$x = 0 true true false
$x = false true true false
$x = [] true true false
$x 未定义 false true true + Notice

从表中可以总结出一句口诀:isset() 只排除 null,empty() 排除一切假值,is_null() 只认 null。

六、面试常见追问与答题思路

追问 1:判断一个变量“有值”应该用哪个?

如果业务含义是“存在且不为空”,通常用 !empty($var);如果业务含义是“存在即可,哪怕是 0 或空字符串”,则应该用 isset($var)关键不是哪个函数更好,而是先明确业务对“空”的定义。

追问 2:empty()!isset() 有什么区别?

!isset($x)$x = null$x 未定义时都为 true;而 empty($x)$x = 0$x = '' 时也为 true。所以 empty() 的范围比 !isset() 大得多。

追问 3:为什么 isset($arr['key'])array_key_exists() 快?

因为 isset() 是语言结构,不涉及函数调用开销,且它对 null 值直接返回 false。如果数组中某个键的值可能是 null,而你仍想判断键是否存在,就必须用 array_key_exists()

追问 4:empty() 能判断对象属性吗?

可以,empty($obj->prop) 是合法的。但如果 $obj 本身未定义,会报错;此时应先 isset($obj) 或用 empty($obj->prop) 配合对象存在性判断。

七、实战建议

  1. 表单校验:不要用 empty() 判断用户输入,尤其是可能为 "0" 的字段,改用 isset() 加显式的长度或类型判断。
  2. 数组取值:优先 isset($arr['k']),需要区分 null 与不存在时用 array_key_exists()
  3. 严格比较:在关键逻辑里,用 === null 代替 is_null() 有时更直观,性能也略好。
  4. 避免 Notice:任何可能未定义的变量,先用 isset() 探测,再读取。

结语

isset()empty()is_null() 的区别,本质上不是三个函数的区别,而是三种对“空”和“存在”的定义。面试官问这道题,考的不是记忆力,而是你是否理解 PHP 的弱类型语义,以及是否在真实项目里踩过坑。

回答时如果能主动说出 empty('0') 的陷阱、is_null() 对未定义变量报 Notice 这些细节,基本就能从“背过八股”升级为“真正用过 PHP”。

未经允许不得转载:任鹏个人博客 » PHP 面试题:isset、empty、is_null 到底有什么区别

赞 (0) 打赏

评论 0

取消
  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏