默认情况下 json_decode() 返回 stdClass 对象,需传入 true 参数才返回关联数组;一维 JSON 数组解码后为索引数组,可直接 foreach 遍历,但须注意类型判断。

json_decode() 返回的是对象还是数组?
默认情况下 json_decode() 返回的是 stdClass 对象,不是数组 —— 这是遍历时出错的最常见原因。比如 foreach($data as $k => $v) 会直接报 Fatal error: Cannot use object of type stdClass as array。
解决办法很简单:传入第二个参数 true,强制返回关联数组:
json_decode($json_string, true)
不加 true 就得用对象语法访问,比如 $data->name;加了才能用 $data['name'] 和 foreach 遍历。
遍历一维 JSON 数组(如 ["a","b","c"])
这种结构解码后是索引数组,foreach 最直接:
立即学习“PHP免费学习笔记(深入)”;
$arr = json_decode('["apple","banana","cherry"]', true);
foreach ($arr as $index => $value) {
echo "$index: $value\n";
}
注意点:
Miller (mlr) 是一个命令行工具,用于查询、整形和重新格式化名称索引数据,如 CSV、TSV、JSON 和 JSON Lines。它将 awk、sed、cut、join 和 sort 的功能整合到一个专为结构化数据处理而构建的单一工具中。
- 如果原始 JSON 是
[1,2,3],$value是整型,不是字符串 - 用
is_array()或is_object()提前判断类型,避免对非数组调用foreach - 不要用
for($i=0; $i<count> —— <code>count()在大数组里反复计算,性能差
遍历嵌套 JSON(如 {"users":[{"id":1,"name":"Tom"}]})
先确保整个结构都转成数组(始终带 true),再逐层检查是否为数组再遍历:
$data = json_decode($json, true);
if (isset($data['users']) && is_array($data['users'])) {
foreach ($data['users'] as $user) {
if (isset($user['name'])) {
echo $user['name'] . "\n";
}
}
}
关键习惯:
- 每次取子键前用
isset()或array_key_exists()防止Notice: Undefined index - 嵌套层级深时,别写
$data['a']['b']['c']['d']这种链式访问 —— 任一层缺失就报错 - 用
??空合并操作符(PHP 7+)快速兜底:$user['email'] ?? 'no email'
遇到 null 或 false 时遍历中断怎么办?
json_decode() 失败时返回 null,而 null、false、空数组在 foreach 中都不会报错但也不执行循环体 —— 表现像“静默失败”。
必须主动检查解码结果:
$data = json_decode($json, true);
if (json_last_error() !== JSON_ERROR_NONE) {
throw new InvalidArgumentException('Invalid JSON: ' . json_last_error_msg());
}
if (!is_array($data)) {
throw new InvalidArgumentException('JSON did not decode to array');
}
常见陷阱:
- JSON 字符串含 UTF-8 BOM 或不可见控制字符,
json_decode()会静默失败 - 用
trim($json)去首尾空白,再检查json_last_error() -
json_decode()对超大 JSON 可能因内存限制返回null,需配合ini_get('memory_limit')排查
真正麻烦的从来不是怎么写 foreach,而是没确认 json_decode() 成功返回了数组,或者忘了嵌套结构里某一层根本不存在。


















