以前對 bind 一直模模糊糊的,今天就再從官網捋一下
必須謹慎對待JSX回調函數中的 this,在 javascript 中,class 的方法默認不會綁定 this。如果你忘記綁定 this.handleClick 並把它傳入了onClick,當你調用這個函數的時候 this 的值會變為 undefined
class Toggle extends React.Component {
constructor(props) {
super(props);
this.state = {isToggleOn: true};
// 為了在回調中使用 `this`,這個綁定是必不可少的
this.handleClick = this.handleClick.bind(this);
}
handleClick() {
this.setState(state => ({
isToggleOn: !state.isToggleOn
}));
}
render() {
return (
<button onClick={this.handleClick}>
{this.state.isToggleOn ? 'ON' : 'OFF'}
</button>
);
}
}
ReactDOM.render(
<Toggle />,
document.getElementById('root')
);
如果覺得bind 很麻煩,那么就使用箭頭函數(官網:如果你正在使用實驗性的 public class fields 語法,你可以使用 class fields 正確的綁定回調函數)
class LoggingButton extends React.Component {
// 此語法確保 `handleClick` 內的 `this` 已被綁定。
// 注意: 這是 *實驗性* 語法。
handleClick = () => {
console.log('this is:', this);
}
render() {
return (
<button onClick={this.handleClick}>
Click me
</button>
);
}
}
如果你沒有使用 class fields 語法,你可以在回調中使用箭頭函數:
此語法問題在於每次渲染 LoggingButton 時都會創建不同的回調函數。在大多數情況下,這沒什么問題,但如果該回調函數作為 prop 傳入子組件時,這些組件可能會進行額外的重新渲染。我們通常建議在構造器中綁定或使用 class fields 語法來避免這類性能問題。(所以還是手動綁定一下的比較好)
class LoggingButton extends React.Component {
handleClick() {
console.log('this is:', this);
}
render() {
// 此語法確保 `handleClick` 內的 `this` 已被綁定。
return (
<button onClick={() => this.handleClick()}>
Click me
</button>
);
}
}