研究ノート-reactのライフサイクルフック機能


反応のライフサイクルは、コンポーネントの作成、コンポーネントの更新、コンポーネントの破棄の3つの段階に大別されます。また、クラスコンポーネントのみにライフサイクルフック関数があり、関数コンポーネントにはありません。

図1.Reactライフサイクルフック機能

1.コンポーネントの作成: 

図1に、ライフサイクルのフック機能の実行シーケンスを示します。

1.コンストラクター():

データは、this.state割り当てオブジェクトによって初期化できます。

イベントハンドラーのインスタンスをバインドします。

constructor(props) {
    super(props);
    this.state = {
        a: 10,
        b: 100
   };
   this.changeName = this.changeName.bind(this);
}

コンポーネントの作成時に1回だけ実行され、それ以降は実行されません。

2.static getDerivedStateFromProps():

この関数は、初期値をサブコンポーネントとしてコンポーネントに割り当てるために使用され、コンポーネントは独自の状態でデータを変更できます。

通常、判断は関数内で行われます。コンポーネントが独自の状態でデータを変更する場合、親コンポーネントからの小道具のデータは必要ありません。

これは、コンポーネントの作成フェーズと更新フェーズで呼び出されます。

このポインターはなく、2つのパラメーターがあります。最初のパラメーターは親コンポーネントからの小道具のデータであり、2番目のパラメーターはコンポーネントの状態のデータです。

オブジェクトまたはnullを返す必要があります。オブジェクトの場合は、このコンポーネントの状態にマージされます。

static getDerivedStateFromProps(nextProps, prevState) {
    if(nextProps.b !== prevState.prevProps.b) {
        return {
            b: nextProps.b,
            prevProps: { b: nextProps.b }
        };
    }else
        return null;
}

3.componentWillMount()|| UNSAFE_componentWillMount():

この関数でsetStateを呼び出しても、追加のレンダリングはトリガーされません。ただし、この関数はコンストラクターで直接実装できます。したがって、この関数は意味がなく、基本的に廃止された状態にあります。

4.render(): 

レンダリングページの主要部分。一部の操作を実装できますが、jsxオブジェクトを返す必要があります。

コアコードは繰り返し呼び出され、パフォーマンスの最適化を実現するために不要なrender()関数呼び出しの数を減らします。

render() {
    // 核心代码,会被反复调用
    console.log("render函数运行了");
    return (
        <div>这是个人中心
            <Child b ={this.state.b}></Child>
        </div>
    );
}

 5.componentDIdMount():

コンポーネントがマウントされた後に呼び出されます。コンポーネントの取り付けは、DOMツリーに挿入することです。

この関数では、通常、ajaxリクエストコンポーネントに必要な動的データが送信されます。

ここでsetStateを呼び出すと、render()関数がトリガーされます。

componentDidMount() {
    // 组件挂载完毕
    let listMain = await http("/category/list/0");
    this.setState({  listMain });
    this.changeCategory(listMain[0].id);
}

 2.コンポーネントの更新:

コンポーネントの更新をトリガーする方法:

1.このコンポーネントはそれ自体でsetStateを呼び出し、再レンダリング(再レンダリング)をトリガーします。

2.親コンポーネントが再レンダリングをトリガーし、子コンポーネントが再レンダリングされます。

3.小道具の変更により、このコンポーネントの再レンダリングがトリガーされます。

1.componentWillReceiveProps()|| UNSAFE_componentWillReceiveProps():

このコンポーネントは、コンポーネントが更新されたときに呼び出されます。通常、次の目的で使用されます。小道具の値が変更された場合、小道具の値の変更に応じて、この関数で対応する操作を実行します。

このコンポーネントは基本的に廃止されました。componentDidUpdateで対応する操作を実行できます。

2.static getDerivedStateFromProps():

操作は、コンポーネントが作成されたときと同じです。詳細については、コンポーネントの作成を参照してください。

3.shouldComponentUpdate():

この関数は、主にreacrのパフォーマンスを最適化するために使用されます。

関数は明示的にtrueまたはfalseを返す必要があります。

2つのパラメーター。最初のパラメーターはnextProps:有効になりそうなprops値で、2番目のパラメーターはnextState:有効になりそうな状態値です。このポインタの現在の値を取得します。

不要な更新を減らすための適切なロジックを記述します。falseを返すと、下向きに実行されないため、レンダリングの数が減り、パフォーマンスが最適化されます。

shouldComponentUpdate(nextProps){
    console.log("child组件的shouldComponentUpdate运行了");
    return this.props.b !== nextProps.b;
}

// 如果不写默认返回true

レンダリング最適化のコードは次のとおりです。

shouldComponentUpdate(nextProps){
    let keys = Object.keys(nextProps);
    for(let i = 0; i < keys.length; i++) {
        if(this.props[keys[i]] !== nextProps[keys[i]] ) return true;
    }
    return false;
}

 これは、reactのpureComponentから継承されたクラスコンポーネントのデフォルトのshouldComponentUpdate()関数と同等です。 

import React, {PureComponent} from 'react';

class Child extends PureComponent {}

PureComponentは、小道具のすべてのプロパティを比較し、最初に現在のコンポーネントを再レンダリングする必要があるかどうかを判断します。

ただし、PureComponentは、プロパティ値の単純な「浅い比較」のみを実行します。

値型の場合、浅い比較で問題ありません。参照型の場合、メモリ内のアドレスが同じであるかどうかのみを比較し、詳細レベルの比較は実行しません。

異なるアドレスと同じコンテンツを持つ参照型が渡された場合、PureComponentは詳細な比較を実行できません。

ユースケース:コンポーネントがクラスコンポーネントであることがわかっていて、このクラスコンポーネントをパフォーマンスのために最適化する必要がある場合。

最大の落とし穴:親コンポーネントが参照型のデータを子コンポーネントに渡す場合、値を渡すときに直接バインドすることはできません。例えば: 

// 错误写法
<Child b ={this.state.b} changeName={this.changeName.bind(this)}></Child>

// 正确写法
changeName = () => {};
<Child b ={this.state.b} changeName={this.changeName}></Child>

4.componentWillUpdate()|| UNSAFE_componentWillUpdate():

このメソッドは非推奨になりました。componentDidUpdate()を使用して、この関数の関数を置き換えることができます。

dom情報を読み取る必要がある場合は、代わりにgetSnapshotBeforeUpdateを使用できます。

componentWillUpdate(){
    // 基本废弃,一般不用了。改名了UNSAFE_componentWillUpdate
    console.log("componentWillUpdate函数运行了");
}

5.render():

更新段階のレンダリングでは、コンポーネントのdomノードを新しいデータに従ってレンダリングできます。domノードは前回と比較され、変更するさまざまなノードが見つかります。すべてのDOMノードが再レンダリングされるわけではありません。

6.getSnapshotBeforeUpdate():

通常、この関数でいくつかのdom操作を実行します。スクロール位置を記録します。

例:スクロール可能なページ。突然更新した後、この関数にその位置を記録し、それをcomponentDidUpdate()関数に渡す必要があります。更新が終了すると、その位置に戻ることができます。

2つのパラメータがあります:prevProps、prevState、その内容は上記と同じです。

値を返す必要があります

getSnapshotBeforeUpdate(prevProps, prevState){
    return { y: 50 }
}
componentDidUpdate(prevProps, prevState, snapshot){
    console.log(snapshot) // { y: 50 }
}

7.componentDidUpdate():

この機能は、主に更新が完了したときに実行されます。

2つのパラメーターがあります。最初のパラメーターはprevPropsで、更新前のprops値であり、2番目のパラメーターは更新前の状態の値を表します。現在の値はthis.propsです。3番目のパラメーターは、getSnapshotBeforeUpdate()によって渡されるデータです。

実装は、vueでの監視の監視に似ています。更新前後のデータを比較する。

この関数は、最新の状態に対応するdomが更新されたことを示しているため、最新のdomでいくつかのカスタム操作を実行できます。

// 模拟vue中的watch监听
componentDidUpdate(prevProps,prevState) {
    if(prevState.a !== this.state.a) {
        console.log("a变量");
    }
}

// 对最新的dom做些自定义操作
// 例如使用插件监听滚动

3.コンポーネントの破壊:

使用されなくなったコンポーネント、または長期間使用されていないコンポーネントは、破棄する必要があります。

1.componentWillUnmount():

 この関数は、主に関連するメモリスペースとリソースを解放するために使用されます。

// 组件销毁
componentWillUnmount() {
    // 释放当前组件相关的内存和资源
    console.log("componentWillUnmount运行了")
}

上記はreactのライフサイクルのフック機能であり、さまざまな機能を通じてさまざまな機能を実現できます。

親コンポーネントと子コンポーネントのライフサイクルフック関数の実行シーケンスは次のとおりです。

親コンポーネントのコンストラクター関数とレンダリング関数は子コンポーネントの前に実行され、子コンポーネントのcomponentDidMountとcomponentDidUpdateは親コンポーネントの前に実行されます。

おすすめ

転載: blog.csdn.net/qq_41339126/article/details/109504150