JavaScript怎样解析JSON数据【教程】

JSON.parse()是解析JSON的标准方法,常见错误包括输入非合法JSON字符串、未转义字符、单引号或缺少引号、尾逗号;reviver用于解析后转换值;需区分服务端返回的是字符串还是已解析对象;不支持循环引用和大文件,应避免同步阻塞调用。

JavaScript 解析 JSON 数据不需要额外库,JSON.parse() 就是标准且唯一推荐的方式;但用错参数、忽略错误、混淆字符串与对象,是绝大多数人踩坑的根源。

为什么 JSON.parse() 会报 “Unexpected token” 错误

这不是语法问题,而是输入根本不是合法 JSON 字符串。常见原因包括:

  • 后端返回的是 HTML(比如 500 页面)或纯文本,却被当成了 JSON
  • 字符串里有未转义的换行、制表符或 Unicode 控制字符(如 \u2028\u2029
  • 用了单引号代替双引号,或键名没加引号({'name': 'Alice'}{name: 'Alice'} 都非法)
  • 末尾多了逗号({"a": 1,} 在严格 JSON 中不被接受)

调试时先 console.log(typeof data, data),确认它是 string 类型且内容可读。

JSON.parse() 的第二个参数:reviver 函数怎么用

它不是用来“修复格式”的,而是对已成功解析的

值做逐层转换,常用于类型还原或字段过滤:

const json = '{"date":"2025-10-05","count":42}';
const obj = JSON.parse(json, (key, value) => {
  if (key === 'date') return new Date(value);
  if (key === 'count' && typeof value === 'number') return value * 2;
  return value;
});
// obj.date 是 Date 实例,obj.count 是 84

注意:reviver 会遍历所有键(包括嵌套对象和数组元素),返回 undefined 会删掉该属性;不要在其中修改原始数据结构,否则行为不可预测。

服务端返回的数据是 JSON 字符串还是已解析对象

取决于你用的是什么请求方式:

  • fetch().then(res => res.json()):自动调用 JSON.parse(),返回 Promise,resolve 值已是 JS 对象
  • XMLHttpRequestaxios 默认也做自动解析(response.data 是对象)
  • 但如果你手动取了 res.responseTextres.data 的原始字符串字段,就必须自己调用 JSON.parse()

混淆这两者会导致 JSON.parse() is not a function(传入了对象)或 Cannot convert object to primitive(对对象再 parse)。

遇到循环引用或超大 JSON 怎么办

JSON.parse() 本身不支持循环引用,也不处理流式解析。如果数据来自文件或长响应体:

  • 前端直接解析几 MB 的 JSON 很容易卡死主线程 —— 考虑用 Web Worker 搬到后台
  • 真有循环引用,说明数据不该走 JSON(JSON 标准不支持),应改用 structuredClone() 或 MessageChannel 序列化
  • 调试时可用 JSON.parse(text.slice(0, 200)) 截断预览开头,快速判断是否结构异常

最常被忽略的一点:JSON.parse() 是同步阻塞操作,别在高频事件(如 input)里无节制调用,也别假设它总能“兜住”后端发来的任意格式。