返回

派生类 Proxy 方法中未定义的 `this`,如何解决?

javascript

派生类 Proxy 方法中未定义的 this

问题

当你在派生类中定义一个 Proxy 对象来覆盖/代理库类方法时,派生类构造函数中的 this 可能是未定义的。这可能会导致执行异常,从而无法正确覆盖/代理函数。

原因分析

Proxy 陷阱是在一个新的执行上下文中调用的,因此 this 绑定到 Proxy 而不是派生类的实例。

解决方法

有几种方法可以解决此问题并成功覆盖/代理库类方法:

  • 使用箭头函数: 箭头函数会自动绑定 this 上下文。
  • 使用 bind() 方法: bind() 方法可用于显式绑定 this 上下文。
  • 使用 Function.prototype.call()Function.prototype.apply() 方法: 这些方法可用于调用 Proxy 陷阱并明确绑定 this 上下文。

代码示例

使用箭头函数:

class Building extends Structure {
    constructor(conditionfunc, args) {
        super(args);     

        this.addDoors = new Proxy(this.addDoors, {
            apply: (target, thisArg, argumentsList) => {
                // ...
            }
        })
    }
}

使用 bind() 方法:

class Building extends Structure {
    constructor(conditionfunc, args) {
        super(args);     

        this.addDoors = this.addDoors.bind(this);
        this.addDoors = new Proxy(this.addDoors, {
            apply: (target, thisArg, argumentsList) => {
                // ...
            }
        })
    }
}

使用 Function.prototype.call()Function.prototype.apply() 方法:

class Building extends Structure {
    constructor(conditionfunc, args) {
        super(args);     

        this.addDoors = new Proxy(this.addDoors, {
            apply: function(target, thisArg, argumentsList) {
                target.apply(thisArg, argumentsList);
            }
        })
    }
}

注意: 使用箭头函数时,无法使用 arguments 对象。你必须显式传递参数。

结论

通过遵循本文提供的方法,你可以解决 this 未定义的问题,并在派生类中成功覆盖/代理库类方法。根据你的特定需求和偏好,选择最适合你情况的方法。

常见问题解答

  1. 为什么派生类中的 this 是未定义的?

    • 因为 Proxy 陷阱是在一个新的执行上下文中调用的,因此 this 绑定到 Proxy 而不是派生类的实例。
  2. 如何绑定 this 上下文?

    • 可以使用箭头函数、bind() 方法、Function.prototype.call()Function.prototype.apply() 方法。
  3. 使用箭头函数的注意事项是什么?

    • 箭头函数不能使用 arguments 对象。你必须显式传递参数。
  4. 为什么使用 bind() 方法的解决方案不起作用?

    • bind() 方法只能在调用 Proxy 陷阱之前绑定 this 上下文。它不能在派生类的构造函数中使用。
  5. 在派生类中覆盖/代理库类方法时,还需要考虑哪些其他事项?

    • 确保条件函数正确验证参数,只有在满足条件时才允许执行。