React中的事件处理为什么要bind this?
个人总结:
问: 请给我讲一下React中的事件处理为什么要bind this?
答: 好的,比如说我写了一个类组件,有个onClick属性 ,onClick={ this.fun },如果不bind肯定是不行的,下面讲一下为什么要bind this:
首先我们知道React是通过创建虚拟DOM 然后将虚拟DOM生成真实的DOM 最后插入到页面中,
而React生命周期中render方法的作用就是将虚拟DOM渲染成真实DOM
看一下这篇文章 https://github.com/hujiulong/blog/issues/4
这里提到了render的实现 render将"on+大写字母"开头的事件属性 转化为"on+小写字母"开头的属性 ,并生成真实DOM,生成真实DOM的同时
把这个函数赋值过去。
( 这篇文章只是一个简要的示例,实际情况更为复杂)
在JSX语法中: onClick={ function } onClick这个属性本身只是一个"中间变量"。将函数赋值给onClick这个中间变量,后面要进行JSX语法转化,将JSX组件转换成Javascript对象,进而转换成真实DOM。
把onClick作为中间变量,指向一个函数的时候,后面的一系列处理中,使用onClick这个中间变量所指向的函数,里面的this会自然丢失掉了,不是再指向react组件实例了。
预备知识点:JS中的this是由函数调用者调用的时候决定的。
obj:{
fun:function(){ console.log(this) }
}
obj.fun() //obj
let var = obj.fun()
var() // window||undefined
在类组件的render函数中 将函数fun赋给真实的属性的时候 有点类似于做了这样的操作:
class Cat {
sayThis () {
console.log(this); // 这里的 `this` 指向谁?
}
exec (cb) {
cb();
}
render () {
this.exec(this.sayThis);
}
}
const cat = new Cat();
cat.render(); // 输出结果是什么?
当把一个函数作为callback传递给另一个函数的时候,这个函数的this一定是会丢失的,
相当于是 let var = function () { ..} ; var();
所以会出现这种问题。
延伸一下,为什么React没有自动的把bind集成到render方法中呢?
答:因为render函数会被多次调用,每次都要bind会影响性能,所以官方建议你自己在constructor中手动bind达到性能优化。