为何Error子类构造函数中需调用Object.setPrototypeOf(this, ...)?
为什么要在自定义Error类中添加
Object.setPrototypeOf(this, DatabaseConnectionError.prototype); 这行代码是为了修复ES6继承内置对象(比如Error)时的原型链异常问题,具体原因如下:
内置构造函数的特殊处理:像
Error、Array这类原生内置对象的构造函数,在ES6早期实现中有特殊逻辑——当你调用super()创建实例后,this的原型链并没有自动指向子类的prototype,而是仍然绑定到内置类的原型(比如Error.prototype)。破坏继承关系的判断:如果不加这行代码,你用
instanceof判断实例是否属于DatabaseConnectionError时会返回false,比如:const err = new DatabaseConnectionError(); console.log(err instanceof DatabaseConnectionError); // 无该行代码时输出false这显然违背了我们继承类的初衷,加上之后才能让
instanceof判断正常工作,保证继承关系的正确性。保证子类属性/方法的访问:虽然现在类字段语法(比如这里的
reason)能直接挂载到实例上,但如果子类有定义在prototype上的方法,原型链错误会导致这些方法无法通过实例正常访问。
另外要说明:这个问题在现代JavaScript引擎中已经被修复,但为了兼容旧版本的Node.js或浏览器,很多项目依然会保留这行代码做兼容处理。
内容的提问来源于stack exchange,提问作者Yang Chandler
相关产品推荐
相关产品推荐

