- 前言
- 綁定 this 的方式一:bind()
- 綁定 this 并給函數傳參 的方式二:構造函數里設置 bind()
- 綁定 this 并給函數傳參 的方式三:箭頭函數【薦】
前言
我們先來看下面這段代碼:
components/MyComponent.jsx
import React from "react";export default class MyComponent extends React.Component {constructor(props) {super(props);this.state = {msg: "這是 MyComponent 組件 默認的msg"};}render() {return (<div><h1>綁定This并傳參</h1><input type="button" value="綁定this并傳參" onClick={this.changeMsg} /><h3>{this.state.msg}</h3></div>);}changeMsg() {// 注意:這里的changeMsg()只是一個普通方法。因此,在觸發的時候,這里的 this 是 undefinedconsole.log(this); // 打印結果:undefinedthis.setState({msg: "設置 msg 為新的值"});}
}
上面的代碼中,點擊按鈕,執行 changeMsg() 方法,嘗試修改 this.state.msg 的值。但是,這個方法執行的時候,是會報錯的:
Uncaught TypeError: Cannot read property 'setState' of null
而且,打印this的結果也是 undefined。這是為啥呢?因為這里的 this 并不是指向 MyComponent 組件本身。
那如何讓 changeMsg() 方法里面的 this,指向MyComponent 組件呢?辦法總是有的,比如說,將changeMsg() 修改為箭頭函數:
changeMsg = () => {console.log(this); // 打印結果:MyComponent 組件this.setState({msg: "設置 msg 為新的值"});};
那么,除了箭頭函數可以 綁定 this,還有沒有其他的方式呢?我們接下來講一講。
綁定 this 的方式一:bind()
代碼舉例:
import React from "react";export default class MyComponent extends React.Component {constructor(props) {super(props);this.state = {msg: "這是 MyComponent 組件 默認的msg"};}render() {return (<div><h1>綁定This并傳參</h1>{/* bind 的作用:為前面的函數,修改函數內部的 this 指向。讓 函數內部的this,指向 bind 參數列表中的 第一個參數 */}<inputtype="button"value="綁定this并傳參"onClick={this.changeMsg1.bind(this)}/><h3>{this.state.msg}</h3></div>);}changeMsg1() {this.setState({msg: "設置 msg 為新的值"});}
}
上方代碼中,我們為什么用 bind(),而不是用 call/apply 呢?因為 bind() 并不會立即調用,正是我們需要的。
注意:bind 中的第一個參數,是用來修改 this 指向的。第一個參數后面的所有參數,都將作為函數的參數傳遞進去。
我們來看看通過 bind() 是怎么傳參的。
通過 bind() 綁定this,并給函數傳參:
import React from "react";export default class MyComponent extends React.Component {constructor(props) {super(props);this.state = {msg: "這是 MyComponent 組件 默認的msg"};}render() {return (<div><h1>綁定This并傳參</h1>{/* bind 的作用:為前面的函數,修改函數內部的 this 指向。讓 函數內部的this,指向 bind 參數列表中的 第一個參數 */}<input type="button" value="綁定this并傳參" onClick={this.changeMsg1.bind(this, "編程的一拳超人啊", "編程的一拳超人啊")} /><h3>{this.state.msg}</h3></div>);}changeMsg1(arg1, arg2) {this.setState({msg: "設置 msg 為新的值" + arg1 + arg2});}
}
綁定 this 并給函數傳參 的方式二:構造函數里設置 bind()
我們知道,構造函數中的 this 本身就是指向組件的實例的,所以,我們可以在這里做一些事情。
代碼舉例:
import React from "react";export default class MyComponent extends React.Component {constructor(props) {super(props);this.state = {msg: "這是 MyComponent 組件 默認的msg"};// 綁定 this 并給函數傳參的方式2: 在構造函數中綁定并傳參// 注意:當一個函數調用 bind 改變了this指向后,bind 函數調用的結果,有一個【返回值】,這個值,就是被改變this指向后的函數的引用。// 也就是說: bind 不會修改 原函數的 this 指向,而是改變了 “函數拷貝”的this指向。this.changeMsg2 = this.changeMsg2.bind(this, "編程的一拳超人恩", "編程的一拳超人恩");}render() {return (<div><h1>綁定This并傳參</h1><input type="button" value="綁定this并傳參" onClick={this.changeMsg2} /><h3>{this.state.msg}</h3></div>);}changeMsg2(arg1, arg2) {this.setState({msg: "設置 msg 為新的值" + arg1 + arg2});}
}
上方代碼中,需要注意的是:當一個函數調用 bind 改變了this指向后,bind 函數調用的結果,有一個【返回值】,這個值,就是被改變this指向后的函數的引用。也就是說: bind 不會修改 原函數的 this 指向,而是改變了 “函數拷貝”的this指向。
綁定 this 并給函數傳參 的方式三:箭頭函數【薦】
第三種方式用得最多。
代碼舉例:
import React from "react";export default class MyComponent extends React.Component {constructor(props) {super(props);this.state = {msg: "這是 MyComponent 組件 默認的msg"};}render() {return (<div><h1>綁定This并傳參</h1><inputtype="button"value="綁定this并傳參"onClick={() => {this.changeMsg3("編程的一拳超人3", "編程的一拳超人3");}}/><h3>{this.state.msg}</h3></div>);}changeMsg3 = (arg1, arg2) => {// console.log(this);// 注意:這里的方式,是一個普通方法,因此,在觸發的時候,這里的 this 是 undefinedthis.setState({msg: "綁定this并傳參的方式3:" + arg1 + arg2});};
}