json.stringify 跳过三类属性:不可枚举属性、值为函数/undefined/symbol 的属性、原型链上的属性;仅序列化对象自身可枚举且值为合法 json 类型(字符串/数字/布尔/null/数组/普通对象)的属性。

JavaScript 对象属性的可枚举性直接影响 JSON.stringify() 的输出结果:它只会序列化对象**自身**的、**可枚举的**(enumerable: true)、且值为**有效 JSON 类型**(字符串、数字、布尔值、null、数组、普通对象)的属性;所有不可枚举属性一律被忽略。
哪些属性会被 JSON.stringify 跳过?
以下三类属性在调用 JSON.stringify(obj) 时不会出现在最终字符串中:
-
不可枚举属性:通过
Object.defineProperty(obj, 'key', { value: ..., enumerable: false })显式设置的属性 -
函数、undefined、Symbol 类型的值:即使属性本身可枚举,只要值是函数或
undefined或Symbol,该属性就会被静默丢弃 -
原型链上的属性:无论是否可枚举,
JSON.stringify只处理对象自身的属性,不遍历原型
一个直观的例子
看这段代码:
const user = { name: 'Alice', age: 30 };
Object.defineProperty(user, 'id', { value: 1001, enumerable: false });
Object.defineProperty(user, 'toString', { value: () => 'custom', enumerable: true });
console.log(JSON.stringify(user));
// 输出:{"name":"Alice","age":30}
// "id" 因不可枚举被跳过;"toString" 虽可枚举但值是函数,也被跳过
如何确认某个属性是否会影响 JSON.stringify?
可以结合两个检查快速判断:
- 用
obj.propertyIsEnumerable('key')确认是否可枚举(注意:只检测自身属性,不查原型) - 用
typeof obj.key和obj.key === undefined判断值类型是否合法(函数、undefined、Symbol 都不行) - 更完整的方式是查看属性描述符:
Object.getOwnPropertyDescriptor(obj, 'key'),观察enumerable字段和value类型
常见误区提醒
很多人误以为“属性存在就能被 JSON 化”,其实关键在两点:一是它必须是对象自身的可枚举属性,二是它的值必须能映射为标准 JSON 类型。比如:
- 类实例上的方法(
class A { method() {} })默认不可枚举 → 不会出现在 JSON 中 - 内置原型方法(如
Array.prototype.map)不可枚举 → 安全,不影响序列化 - 手动设为
enumerable: true的函数属性,依然不会被序列化 —— 可枚举性管“是否露面”,JSON.stringify 还额外过滤值类型
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











