应使用 object.getprototypeof() 而非 __proto__,因后者是非标准、已弃用、可写且兼容性差;前者是 es5 标准 api,安全稳定,支持所有现代环境并提供明确错误提示。

直接用 Object.getPrototypeOf(),别碰 __proto__ —— 这不是风格偏好,而是兼容性、规范性和可维护性的硬性要求。
为什么 __proto__ 不该出现在生产代码里
__proto__ 是早期浏览器私有实现,从未被写入 ECMAScript 标准。它在部分环境(如严格模式下的某些对象、Web Workers、某些嵌入式 JS 引擎)中不可访问或行为不一致;V8 和 SpiderMonkey 已明确将其标记为“已弃用”,未来版本可能移除。更重要的是,它是个可写属性,容易被混淆代码或意外赋值污染,导致原型链断裂或调试困难。
Java Maven 项目审查工作流的通用输入处理。当 Java Maven 项目以 ZIP压缩包或 GitLab 仓库 URL 形式提供且需要...时使用。
Object.getPrototypeOf() 的实际优势
- 它是 ES5 正式标准 API,所有现代环境(包括 IE11+、Node.js 0.12+、各主流浏览器)都稳定支持
- 对非法输入(
null、undefined、原始值)会立即抛出TypeError,便于定位问题,而不是静默失败 - 不依赖对象是否暴露
__proto__属性,哪怕对象被Object.create(null)创建,也能安全调用(返回null) - 与
Object.setPrototypeOf()构成配套接口,语义统一、行为可预测
常见误用场景与替代方案
- 想判断数组:不用
obj.__proto__ === Array.prototype,改用Object.getPrototypeOf(obj) === Array.prototype或更稳妥的Array.isArray(obj) - 遍历原型链:不要递归读取
obj.__proto__,改用let p = Object.getPrototypeOf(obj); while (p) { /* 处理 */ p = Object.getPrototypeOf(p); } - 跨 iframe 类型检测失效时:
instanceof不可靠,但Object.getPrototypeOf(iframeObj)返回的是 iframe 内部真实的Array.prototype,可结合Object.prototype.toString.call(iframeObj)做类型识别 - 需要修改原型:用
Object.setPrototypeOf(target, newProto)替代赋值target.__proto__ = newProto,前者有规范保障,后者在严格模式下可能报错
特殊情况下的注意事项
极少数旧环境(如 IE9 或更低版本)确实不支持 Object.getPrototypeOf。若必须兼容,可用降级方案:
function getProto(obj) {
if (Object.getPrototypeOf) return Object.getPrototypeOf(obj);
if (obj.__proto__) return obj.__proto__;
return obj.constructor ? obj.constructor.prototype : null;
}
但请注意:这个 fallback 仅用于兜底,不能作为默认路径;真实项目应通过构建工具(如 Babel + core-js)自动注入 polyfill,而非手动混用 __proto__。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










