中文字幕日韩精品一区二区免费_精品一区二区三区国产精品无卡在_国精品无码专区一区二区三区_国产αv三级中文在线

怎么理解Reacthooks的渲染邏輯

這篇文章主要介紹“怎么理解React hooks的渲染邏輯”,在日常操作中,相信很多人在怎么理解React hooks的渲染邏輯問題上存在疑惑,小編查閱了各式資料,整理出簡單好用的操作方法,希望對大家解答”怎么理解React hooks的渲染邏輯”的疑惑有所幫助!接下來,請跟著小編一起來學(xué)習(xí)吧!

創(chuàng)新互聯(lián)專注為客戶提供全方位的互聯(lián)網(wǎng)綜合服務(wù),包含不限于網(wǎng)站設(shè)計、做網(wǎng)站、寧陵網(wǎng)絡(luò)推廣、小程序開發(fā)、寧陵網(wǎng)絡(luò)營銷、寧陵企業(yè)策劃、寧陵品牌公關(guān)、搜索引擎seo、人物專訪、企業(yè)宣傳片、企業(yè)代運營等,從售前售中售后,我們都將竭誠為您服務(wù),您的肯定,是我們最大的嘉獎;創(chuàng)新互聯(lián)為所有大學(xué)生創(chuàng)業(yè)者提供寧陵建站搭建服務(wù),24小時服務(wù)熱線:028-86922220,官方網(wǎng)址:m.rwnh.cn

由于項目環(huán)境比較復(fù)雜,如果是純class組件,那么就是component、pureComponent、shouldComponentUpdate之類的控制一下是否重新渲染,但是hooks似乎更多場景,接下來一一攻破。

  •  場景一 ,父組件使用hooks,子組件使用class Component

父組件

export default function Test() {      const [state, setState] = useState({ a: 1, b: 1, c: 1 });      const [value, setValue] = useState(11);      return (          <div>              <div>                  state{state.a},{state.b}              </div>              <Button                  type="default"                  onClick={() => {                      //@ts-ignore                      setState({ a: 2, b: 1 });                      //@ts-ignore                      setState({ a: 2, b: 2 });                      console.log(state, 'state');                  }}              >                  測試              </Button>              <hr />              <div>value{value}</div>              <Button                  type="default"                  onClick={() => {                      setValue(value + 1);                  }}              >                  測試              </Button>              <Demo value={state} />          </div>      );  }

子組件

export default class App extends React.Component<Props> {      render() {          const { props } = this;          console.log('demo render');          return (              <div>                  {props.value.a},{props.value.b}              </div>          );      }  }

結(jié)果每次點擊圖中的測試按鈕,子組件Demo都會重新render:

怎么理解React hooks的渲染邏輯

總結(jié):父組件(hook)每次更新,都會導(dǎo)出一個新的state和value對象,子組件肯定會更新(如果不做特殊處理)

  •  場景二,父組件使用hooks,子組件使用class PureComponent 

父組件代碼跟上面一樣,子組件使用PureComponent:

export default function Test() {      const [state, setState] = useState({ a: 1, b: 1, c: 1 });      const [value, setValue] = useState(11);      return (          <div>              <div>                  state{state.a},{state.b}              </div>              <Button                  type="default"                  onClick={() => {                      //@ts-ignore                      setState({ a: 2, b: 1 });                      //@ts-ignore                      setState({ a: 2, b: 2 });                      console.log(state, 'state');                  }}              >                  測試              </Button>              <hr />              <div>value{value}</div>              <Button                  type="default"                  onClick={() => {                      setValue(value + 1);                  }}              >                  測試              </Button>              <Demo value={state} />          </div>      );  }

子組件使用PureComponent:

export default class App extends React.PureComponent<Props> {      render() {          const { props } = this;          console.log('demo render');          return (              <div>                  {props.value.a},{props.value.b}              </div>          );      }  }

結(jié)果子組件依舊會每次都重新render:

怎么理解React hooks的渲染邏輯

總結(jié):結(jié)論同上,確實是依賴的props改變了,因為父組件是hook模式,每次更新都是直接導(dǎo)出新的value和state.

  •  場景三,搞懂hook的setState跟class組件setState有什么不一樣

理論:class的setState,如果你傳入的是對象,那么就會被異步合并,如果傳入的是函數(shù),那么就會立馬執(zhí)行替換,而hook的setState是直接替換,那么setState在hook中是異步還是同步呢?

實踐:

組件A:

export default function Test() {      const [state, setState] = useState({ a: 1, b: 1, c: 1 });      const [value, setValue] = useState(11);      return (          <div>              <div>                  state{state.a},{state.b},{state.c}              </div>              <Button                  type="default"                  onClick={() => {                      //@ts-ignore                      setState({ a: 2 });                      //@ts-ignore                      setState({ b: 2 });                      console.log(state, 'state');                  }}              >                  測試              </Button>              <hr />              <div>value{value}</div>              <Button                  type="default"                  onClick={() => {                      setValue(value + 1);                  }}              >                  測試              </Button>              <Demo value={state} />          </div>      );  }

我將setState里兩次分別設(shè)置了state的值為{a:2},{b:2},那么是合并,那么我最終得到state應(yīng)該是{a:2,b:2,c:1},如果是替換,那么最后得到的state是{b:2}

結(jié)果:

怎么理解React hooks的渲染邏輯

點擊測試按鈕后,state變成了{(lán)b:2},整個value被替換成了{(lán)b:2}

結(jié)論:hook的setState是直接替換,而不是合并

  •  場景四 , 父組件使用class,子組件使用hook

  父組件:

export default class App extends React.PureComponent {      state = {          count: 1,      };      onClick = () => {          const { count } = this.state;          this.setState({              count: count + 1,          });      };      render() {          const { count } = this.state;          console.log('father render');          return (              <div>                  <Demo count={count} />                  <Button onClick={this.onClick}>測試</Button>              </div>          );      }  }

子組件:

interface Props {      count: number;  }  export default function App(props: Props) {      console.log(props, 'props');      return <div>{props.count}</div>;  }

邏輯:父組件(class組件)調(diào)用setState,刷新自身,然后傳遞給hooks子組件,然后自組件重新調(diào)用,更新

怎么理解React hooks的渲染邏輯

  •  場景五

但是我此時需要想實現(xiàn)一個class 組件的 PureComponent一樣的效果,需要用到React.memo

修改父組件代碼為:

export default class App extends React.PureComponent {      state = {          count: 1,          value: 1,      };      onClick = () => {          const { value } = this.state;          this.setState({              count: value + 1,          });      };      render() {          const { count, value } = this.state;          console.log('father render');          return (              <div>                  <Demo count={count} />                  {value}                  <Button onClick={this.onClick}>測試</Button>              </div>          );      }  }

子組件加入memo,代碼修改為:

import React, { useState, memo } from 'react';  interface Props {      count: number;  }  function App(props: Props) {      console.log(props, 'props');      return <div>{props.count}</div>;  }  export default memo(App);

此時邏輯:class組件改變了自身的state,自己刷新自己,由上而下,傳遞了一個沒有變化的props給hooks組件,hooks組件使用了memo包裹自己。

結(jié)果:

怎么理解React hooks的渲染邏輯

我們使用了memo實現(xiàn)了PureComponent的效果,淺比較了一次

  •  場景六,hook,setState每次都是相同的值 

export default class App extends React.PureComponent {      state = {          count: 1,          value: 1,      };      onClick = () => {          const { value } = this.state;          this.setState({              value:   1,          });      };      render() {          const { count, value } = this.state;          console.log('father render');          return (              <div>                  <Demo count={count} />                  {value}                  <Button onClick={this.onClick}>測試</Button>              </div>          );      }  }

結(jié)果:由于每次設(shè)置的值都是一樣的(都是1),hooks不會更新,同class

  •  場景七,父組件和子組件都使用hook

父組件傳入count給子組件

export default function Father() {      const [count, setCount] = useState(1);      const [value, setValue] = useState(1);      console.log('father render')      return (          <div>              <Demo count={count} />              <div>value{value}</div>              <Button                  onClick={() => {                      setValue(value + 1);                  }}              >                  測試              </Button>          </div>      );  }

子組件使用count

export default function App(props: Props) {      console.log(props, 'props');      return <div>{props.count}</div>;  }

結(jié)果:每次點擊測試,都會導(dǎo)致子組件重新render

怎么理解React hooks的渲染邏輯

子組件加入memo

function App(props: Props) {      console.log(props, 'props');      return <div>{props.count}</div>;  }  export default memo(App);

結(jié)果:

怎么理解React hooks的渲染邏輯

子組件并沒有觸發(fā)更新

這里跟第一個案例class的PureComponent不一樣,第一個案例class的PureComponent子組件此時會重新render,是因為父組件hooks確實每次更新都會導(dǎo)出新的value和state。這里是調(diào)用了一次,設(shè)置的都是相同的state.所以此時不更新

  •  場景八,父組件hook,子組件hook,使用useCallback緩存函數(shù)

父組件:

export default function App() {    const [count1, setCount1] = useState(0);    const [count2, setCount2] = useState(0);   const handleClickButton1 = () => {      setCount1(count1 + 1);    };    const handleClickButton2 = useCallback(() => {      setCount2(count2 + 1);    }, [count2]);     return (      <div>        <div>          <Button onClickButton={handleClickButton1}>Button1</Button>        </div>        <div>          <Button onClickButton={handleClickButton2}>Button2</Button>        </div>      </div>    );  }

子組件:

import React from 'react';  const Button = (props: any) => {     const { onClickButton, children } = props;      return (          <>              <button onClick={onClickButton}>{children}</button>              <span>{Math.random()}</span>          </>      );  };  export default React.memo(Button);

結(jié)果:雖然我們使用了memo.但是點擊demo1,只有demo1后面的數(shù)字改變了,demo2沒有改變,點擊demo2,兩個數(shù)字都改變了。

那么我們不使用useCallback看看

父組件修改代碼,去掉useCallback

export default function App() {      const [count1, setCount1] = useState(0);      const [count2, setCount2] = useState(0);      const handleClickButton1 = () => {          setCount1(count1 + 1);      };      const handleClickButton2 = () => {          setCount2(count2+ 1);      };      return (          <div>              <div>                  <Demo onClickButton={handleClickButton1}>Demo1</Demo>              </div>              <div>                  <Demo onClickButton={handleClickButton2}>Demo</Demo>              </div>          </div>      );  }

子組件代碼不變,結(jié)果此時每次都會兩個數(shù)字都會跟著變。

怎么理解React hooks的渲染邏輯

官方對useCallback的解釋:

就是返回一個函數(shù),只有在依賴項發(fā)生變化的時候才會更新(返回一個新的函數(shù))

結(jié)論:

我們聲明的 handleClickButton1 是直接定義了一個方法,這也就導(dǎo)致只要是父組件重新渲染(狀態(tài)或者props更新)就會導(dǎo)致這里聲明出一個新的方法,新的方法和舊的方法盡管長的一樣,但是依舊是兩個不同的對象,React.memo 對比后發(fā)現(xiàn)對象 props 改變,就重新渲染了。

const a =()=>{}  const b =()=>{}  a===b //false

這個道理大家都懂,不解釋了

  •  場景九,去掉依賴數(shù)組中的count2字段 

import React, { useState, useCallback } from 'react';  import Demo from './Demo';  export default function App() {    const [count2, setCount2] = useState(0);    const handleClickButton2 = useCallback(() => {      setCount2(count2 + 1);    }, []);    return (      <Demo         count={count2}        onClickButton={handleClickButton2}      >測試</Demo>    );  }

這樣count2的值永遠(yuǎn)都是0,那么這個組件就不會重導(dǎo)出setCount2這個方法,handleClickButton2這個函數(shù)永遠(yuǎn)不會變化,Button只會更新一次,就是Demo組件接受到的props從0到1到的時候.繼續(xù)點擊,count2也是0,但是props有一次從0-1的過程導(dǎo)致Demo子組件被更新,不過count2始終是0,這非常關(guān)鍵

  •  場景十,使用useMemo,緩存對象,達(dá)到useCallback的效果

使用前

export default function App() {      const [count, setCount] = useState(0);      const [value, setValue] = useState(0);      const userInfo = {          age: count,          name: 'Jace',      };      return (          <div>              <div>                  <Demo userInfo={userInfo} />              </div>              <div>                  {value}                  <Button                      onClick={() => {                          setValue(value + 1);                      }}                  ></Button>              </div>          </div>      );  }

子組件使用了memo,沒有依賴value,只是依賴了count.

但是結(jié)果每次父組件修改了value的值后,雖然子組件沒有依賴value,而且使用了memo包裹,還是每次都重新渲染了

怎么理解React hooks的渲染邏輯

import React from 'react';  const Button = (props: any) => {      const { userInfo } = props;      console.log('sub render');      return (          <>              <span>{userInfo.count}</span>          </>      );  };  export default React.memo(Button);

使用后useMemo

const [count, setCount] = useState(0);  const obj = useMemo(() => {    return {      name: "Peter",      age: count    };  }, [count]);  return <Demo obj={obj}>

很明顯,第一種方式,如果每次hook組件更新,那么hook就會導(dǎo)出一個新的count,const 就會聲明一個新的obj對象,即使用了memo包裹,也會被認(rèn)為是一個新的對象。

看看第二種的結(jié)果:

怎么理解React hooks的渲染邏輯

父組件更新,沒有再影響到子組件了。

到此,關(guān)于“怎么理解React hooks的渲染邏輯”的學(xué)習(xí)就結(jié)束了,希望能夠解決大家的疑惑。理論與實踐的搭配能更好的幫助大家學(xué)習(xí),快去試試吧!若想繼續(xù)學(xué)習(xí)更多相關(guān)知識,請繼續(xù)關(guān)注創(chuàng)新互聯(lián)網(wǎng)站,小編會繼續(xù)努力為大家?guī)砀鄬嵱玫奈恼拢?/p>

網(wǎng)頁名稱:怎么理解Reacthooks的渲染邏輯
網(wǎng)站地址:http://m.rwnh.cn/article16/pdiddg.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供商城網(wǎng)站網(wǎng)站排名、搜索引擎優(yōu)化網(wǎng)站設(shè)計公司、網(wǎng)站建設(shè)云服務(wù)器

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)

營銷型網(wǎng)站建設(shè)
务川| 游戏| 乌兰浩特市| 晋江市| 宝清县| 丰城市| 哈巴河县| 年辖:市辖区| 五常市| 邹城市| 龙游县| 毕节市| 长白| 中超| 翁源县| 云阳县| 堆龙德庆县| 河西区| 油尖旺区| 石楼县| 始兴县| 锡林郭勒盟| 灯塔市| 忻城县| 曲水县| 江津市| 贵定县| 正安县| 东乌珠穆沁旗| 巩义市| 邵东县| 宁阳县| 信宜市| 巧家县| 滦平县| 邮箱| 黄浦区| 德保县| 德钦县| 麻江县| 左贡县|