in操作符自ES3起存在,ES2022扩展支持检测类中私有字段(#field);它判断字符串键是否存在于对象自身或原型链上,不区分自有/继承,不适用于Symbol键或值存在性检测。

in 操作符在 ES6 及后续版本中没有新增语法结构,它本身是 JavaScript 早期就存在的运算符(ES3 起已支持),但 ES2022(即 ES13)起明确扩展了其语义范围:支持检测类中的私有属性(#开头的字段)是否存在。
能判断对象自有或继承的属性键名
对普通对象,in 判断的是属性名(字符串键)是否存在于对象自身或其原型链上:
-
'name' in obj返回true,只要obj自身或任意一层原型上有该键 - 与
obj.hasOwnProperty('name')不同,in不区分自有/继承 - 注意:它检测的是“键是否存在”,不是“值是否为 undefined”或“是否为 null”
对数组只检测索引(下标)是否存在,不检测元素值
in 用于数组时,左侧操作数会被转为字符串,并作为索引键检查:
-
1 in [10, , 30]→false(索引 1 是空槽,无该属性) -
'1' in [10, 20, 30]→true(字符串'1'等价于数字1) -
5 in [1,2,3]→false(索引 5 不存在) - ⚠️ 它不能用来判断某个值(如
2)是否在数组中——那是Array.prototype.includes()的职责
ES2022 起支持检测私有字段(#field)
这是 ES2022(第13版)正式引入的关键增强:
- 仅适用于
class内部定义的私有字段,如#id、#_cache - 写法:
#id in instance,返回布尔值 - 只能在类方法内部或同一词法作用域中使用(不能在外部随意探测)
- 示例:
#token;
constructor(t) { this.#token = t; }
hasToken() { return #token in this; }
}
const u = new User('abc');
u.hasToken(); // true
不能用于 Symbol 属性或不可枚举属性的直接检测
in 对以下情况无效:
-
Symbol('key') in obj→ 始终false(in只处理字符串键) - 通过
Object.defineProperty设置enumerable: false的自有属性,仍会返回true(因为in不关心可枚举性,只看属性存在性) - 想准确判断“自有且可枚举”,应改用
Object.keys(obj).includes(key)


















