React應該如何優雅的綁定事件?

前言

因爲JS的靈活性,咱們在React中其實有不少種綁定事件的方式,然而,其實有許多咱們常見的事件綁定,其實並非高效的。因此本文想給你們介紹一下React綁定事件的正確姿式。

常見兩種種錯誤綁定事件

class ErrorExample1 extends Component {

    balabala(e) {console.log(e)}
    
    render() {
        const { text } = this.state;
        
        return (
          <Wrapper>
            {text}
            <Balabala onClick={(e) => this.balabala(e)}></Balabala>
          </Wrapper>
        )
    }
}
class ErrorExample2 extends Component {
    balabala(e) {console.log(e)}
    
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={this.balabala.bind(this)}></Balabala>
          </Wrapper>
        )
    }
}

這是兩種最多見的React綁定事件代碼,但它爲何是錯誤的?javascript

每當你的text發生變化,就會rerender,只要組件從新render,那就會從新建立新的事件函數,進而綁定事件,這個過程的開銷就是極大極大的浪費。至關於,每次rerender都會建立一次事件函數。java

這聽說是 Best Practice

class Balabala extends Component {
    constructor(p) {
        suprt(p);
        this.balabala = this.balabala.bind(this);
    }
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={this.balabala}></Balabala>
          </Wrapper>
        )
    }
}

然而我更喜歡的姿式

class Balabala extends Component {
    constructor(p) {
        suprt(p);
    }
    醒來記得想我 = (e) => {
        alert('想你了');
    }
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={this.醒來記得想我}></Balabala>
          </Wrapper>
        )
    }
}

利用箭頭函數,幫咱們bind this。避免了在構造函數裏生命一堆的變量。減小鍵盤的敲擊,延長生命。react

固然,還有人會問,這樣的寫法如何傳參呢?之前別人會這樣寫app

class 渣男 extends Component {
    constructor(p) {
        suprt(p);
    }
    醒來記得想我 = (e, text) => {
        alert(text); // alert 滾吧,渣男
    }
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={this.醒來記得想我.bind(e, '滾吧,渣男')}></Balabala>
          </Wrapper>
        )
    }
}

可是其實,咱們能夠這樣傳參,更加簡潔明瞭函數

class 渣男 extends Component {
    constructor(p) {
        suprt(p);
    }
    醒來記得想我 = (text) => (event) => {
        alert(text); // 你渣我也喜歡,由於是你
    }
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={this.醒來記得想我( '你渣我也喜歡,由於是你')}></Balabala>
          </Wrapper>
        )
    }
}

動態綁定

基於這個咱們還能夠針對同一事件修改多個input值,進行事件優化優化

class ChangeMyName extends Component {
  修改渣男名稱 = name => {
    if (!this.handlers[name]) {
      this.handlers[name] = event => {
        this.setState({ [name]: event.target.value });
      };
    }
    return this.handlers[name];  
  }
  
  render() {
    return (
        <>
          <input onChange={this.修改渣男名稱('男神1號')}/>
          <input onChange={this.修改渣男名稱('渣男2號')}/>
        </>
    )
  }
}

旁門左道,邪教!(我的不喜歡而已)

import autoBind from 'react-autobind';

class Balabala extends Component {
    constructor() {
       autoBind(this);
    }
    醒來記得想我 (e) {
        alert('想你了');
    }
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={this.醒來記得想我}></Balabala>
          </Wrapper>
        )
    }
}
import { BindAll } from 'lodash-decorators';

@BindAll()
class Bbb extends Component {}
// 這種寫法等同於 bind
class Bbb extends Component {
    balabala(){}
    render() {
        const { text } = this.state;
        return (
          <Wrapper>
            {text}
            <Balabala onClick={::this.balabala}></Balabala>
          </Wrapper>
        )
    }
}

基本都大同小異吧,就不過多介紹了。看到這裏,你也知道到底應該如何綁定事件了。網站

我的網站: http://meckodo.com
相關文章
相關標籤/搜索