js/ts 这两种传入回调函数的方式有什么区别?

有两个类 Basketball 和 People

class Basketball {
    private test: HTMLElement = document.createElement('div');
    constructor() {
        // 将 test 插入到页面中
    }
    public fibaRule (): void {
        console.log('Fiba rule!');
        this.test.classList.add('fiba-rule');
    }
}

class People {
    private rule: Function;
    constructor ({ rule }: {
        rule: Function;
    }) {
        this.rule = rule;
    }
    public play (): void {
        this.rule();
    }
}
// 

实例化出 basketballInstance 和 peopleInstace
我通过两个方式将 basketballInstance 的 fibaRule 方法 传给 peopleInstace

let basketballInstance = new Basketball();

// 1
let peopleInstace = new People({
    rule: basketballInstance.fibaRule,
});

//2
let peopleInstace = new People({
    rule: () => {
        basketballInstance.fibaRule();
    },
});

然后执行

peopleInstace.play();

通过 1 方式传入的话,console.log('Fiba rule!') 是可以执行,但是 test 会报错 undefined
通过 2 方式就没问题
不知道原因是什么

外面包一层之后,和不包一层有什么不一样吗


还真没想到 this 指向的问题,结合大家的答案说下我得思路,不知道对不对:

  1. new 会改变了函数内部的 this 指向 new 的对象
  2. 所以方式 1 会导致 basketballInstance.fibaRule() 中的 this 指向 peopleInstace 中的 this
  3. 方法 2 用了箭头函数,箭头函数自己是没有 this 的,箭头函数中的 this 指向定义时所在的对象
阅读 2.5k
2 个回答

这个是典型的函数引用,函数执行时this的问题
第一种方式传递调用,this指向的是peopleInstace
第二种方式this指向的是basketballInstance,大多数情况对象.方法调用的适合,this就是点号前面的对象,具体的请查看相关文章

并不在于用你所谓的js/ts方式,而是在于你rule的传递方式。第一种传递方式引用的function并没有绑定到basketballInstance上,所以拿不到test。建议看看js关于this指向的知识

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题