最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

React中useMemo與useCallback區(qū)別以及各自解決什么性能問題、依賴陷阱詳解

 更新時間:2026年05月18日 10:18:24   作者:光影少年  
useCallback和useMemo是一樣的東西,只是入?yún)⒂兴煌?這篇文章主要介紹了React中useMemo與useCallback區(qū)別以及各自解決什么性能問題、依賴陷阱的相關(guān)資料,文中通過代碼介紹的非常詳細(xì),需要的朋友可以參考下

這是 React 面試?yán)锓浅8哳l的問題。你有前端經(jīng)驗(yàn),直接從本質(zhì)、解決的問題、區(qū)別、依賴陷阱、實(shí)際場景理解會更快。

一、先理解 React 為什么會有 useMemo / useCallback

函數(shù)組件每次重新渲染:

function App() {
  const a = 1;

  const fn = () => {
    console.log(a);
  };

  return <Child fn={fn} />;
}

每次 App render:

fn1 !== fn2

函數(shù)是新的引用。

對象也是:

{ name: '張三' } !== { name: '張三' }

新的引用會導(dǎo)致:

  • 子組件重新渲染
  • 大量計(jì)算重復(fù)執(zhí)行
  • memo 失效

所以 React 提供緩存:

緩存值 → useMemo
緩存函數(shù) → useCallback

二、useMemo

作用:

緩存計(jì)算結(jié)果(value)

語法:

const value = useMemo(
  () => expensiveFn(a, b),
  [a, b]
);

等價于:

依賴沒變:
返回上次結(jié)果

依賴變:
重新執(zhí)行計(jì)算

場景1:避免復(fù)雜計(jì)算重復(fù)執(zhí)行

錯誤:

function App({ list }) {

  const total = list.reduce(
      (sum,item)=>sum+item.price,
      0
  );

  return <div>{total}</div>
}

每次 render:

都會重新算:

O(n)

優(yōu)化:

const total = useMemo(() => {
    return list.reduce(
        (sum,item)=>sum+item.price,
        0
    );
},[list]);

只有 list 變:

才重新計(jì)算。

解決問題:

避免高開銷計(jì)算

比如:

  • 排序
sort()
  • filter
filter()
  • reduce
reduce()
  • 大數(shù)據(jù)處理
  • 圖表計(jì)算
  • PDF 導(dǎo)出計(jì)算

你做性能平臺經(jīng)常會遇到。

場景2:保持對象引用穩(wěn)定

錯誤:

<Child options={{
   page:1,
   size:10
}}/>

每次:

{} !== {}

Child 重渲染。

優(yōu)化:

const options = useMemo(() => ({
    page:1,
    size:10
}),[]);

<Child options={options}/>

三、useCallback

作用:

緩存函數(shù)

語法:

const fn = useCallback(() => {

},[deps]);

等價于:

const fn = useMemo(
   ()=>()=>{},
   [deps]
)

所以:

useCallback ≈ useMemo(返回函數(shù))

錯誤:

function App(){

 const click=()=>{
      console.log("點(diǎn)擊")
 }

 return <Child onClick={click}/>
}

每次 render:

click1 != click2

子組件重新渲染。

優(yōu)化:

const click = useCallback(()=>{

},[]);

函數(shù)引用穩(wěn)定。

解決問題:

避免子組件無意義渲染

常搭配:

React.memo()

例如:

const Child = React.memo(
    ({onClick})=>{

}
);

只有:

props變化

才重渲染。

否則:

父更新
↓
子不更新

四、兩者區(qū)別(面試回答)

可直接背:

對比useMemouseCallback
緩存什么函數(shù)
返回計(jì)算結(jié)果函數(shù)
解決問題重復(fù)計(jì)算函數(shù)引用變化
常見用途大數(shù)據(jù)計(jì)算、對象緩存事件函數(shù)緩存
搭配React.memoReact.memo

一句話:

useMemo 緩存結(jié)果
useCallback 緩存方法

五、依賴陷阱(重點(diǎn))

這是面試官最愛問的。

陷阱1:依賴遺漏(閉包陷阱)

錯誤:

const [count,setCount]=useState(0);

const add = useCallback(()=>{
    console.log(count);
},[]);

依賴:

[]

永遠(yuǎn)緩存第一次:

輸出:

0
0
0

不是最新值。

因?yàn)殚]包:

記住舊 count。

應(yīng)寫:

const add = useCallback(()=>{
   console.log(count)
},[count]);

陷阱2:依賴過多導(dǎo)致失效

錯誤:

const options = {
   page,
   size
}

const fn = useCallback(()=>{

},[options]);

每次:

options 新對象

導(dǎo)致:

緩存失效
重新創(chuàng)建函數(shù)

應(yīng):

[page,size]

陷阱3:濫用 useMemo/useCallback

很多人:

const a = useMemo(()=>1,[]);

沒意義。

因?yàn)椋?/p>

緩存也有成本:

比較依賴
存緩存
維護(hù)引用

小計(jì)算:

直接寫:

const a=1;

更快。

陷阱4:以為用了 useCallback 就優(yōu)化了

錯誤:

const fn = useCallback(()=>{},[]);

但:

<Child fn={fn}/>

Child 不是:

React.memo()

仍會渲染。

優(yōu)化失敗。

通常配合:

useCallback + React.memo

六、什么時候不要用

不要:

const fn = useCallback(()=>{},[])
const obj = useMemo(()=>({}),[])

到處包。

會讓代碼:

  • 更復(fù)雜
  • 更難維護(hù)
  • 不一定更快

真正需要時:

用 useMemo

有昂貴計(jì)算:

排序
filter
大列表
圖表
PDF
Excel

用 useCallback

函數(shù)傳給:

React.memo 子組件
useEffect 依賴
事件回調(diào)

面試總結(jié)版(30 秒回答):

useMemo 用來緩存計(jì)算結(jié)果,避免重復(fù)執(zhí)行昂貴計(jì)算;useCallback 用來緩存函數(shù)引用,避免子組件因函數(shù)變化重復(fù)渲染。useMemo 返回值,useCallback 返回函數(shù)。常見陷阱是依賴遺漏導(dǎo)致閉包問題、依賴對象導(dǎo)致緩存失效,以及濫用緩存造成額外開銷。實(shí)際優(yōu)化通常配合 React.memo 使用。

到此這篇關(guān)于React中useMemo與useCallback區(qū)別以及各自解決什么性能問題、依賴陷阱詳解的文章就介紹到這了,更多相關(guān)React useMemo與useCallback區(qū)別內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • React Hooks使用常見的坑

    React Hooks使用常見的坑

    React Hooks 是 React 16.8 引入的新特性,允許我們在不使用 Class 的前提下使用 state 和其他特性。接下來通過本文給大家分享React Hooks使用避坑指南,一起學(xué)習(xí)下吧
    2021-06-06
  • 詳解如何在React中監(jiān)聽鼠標(biāo)事件

    詳解如何在React中監(jiān)聽鼠標(biāo)事件

    React可以通過使用React事件系統(tǒng)來監(jiān)聽鼠標(biāo)事件,您可以在React組件中通過使用特定的事件處理函數(shù)來注冊和處理鼠標(biāo)事件,本文小編講給大家詳細(xì)介紹一下如何在React中監(jiān)聽鼠標(biāo)事件,需要的朋友可以參考下
    2023-09-09
  • 從零開始搭建webpack+react開發(fā)環(huán)境的詳細(xì)步驟

    從零開始搭建webpack+react開發(fā)環(huán)境的詳細(xì)步驟

    這篇文章主要介紹了從零開始搭建webpack+react開發(fā)環(huán)境的詳細(xì)步驟,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2018-05-05
  • 如何去除富文本中的html標(biāo)簽及vue、react、微信小程序中的過濾器

    如何去除富文本中的html標(biāo)簽及vue、react、微信小程序中的過濾器

    這篇文章主要介紹了如何去除富文本中的html標(biāo)簽及vue、react、微信小程序中的過濾器,在vue及react中經(jīng)常會遇到,今天通過實(shí)例代碼給大家講解,需要的朋友可以參考下
    2018-11-11
  • React自定義hooks同步獲取useState的最新狀態(tài)值方式

    React自定義hooks同步獲取useState的最新狀態(tài)值方式

    這篇文章主要介紹了React自定義hooks同步獲取useState的最新狀態(tài)值方式,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-03-03
  • React HOC高階組件深入講解

    React HOC高階組件深入講解

    高階組件就是接受一個組件作為參數(shù)并返回一個新組件(功能增強(qiáng)的組件)的函數(shù)。這里需要注意高階組件是一個函數(shù),并不是組件,這一點(diǎn)一定要注意,本文給大家分享React 高階組件HOC使用小結(jié),一起看看吧
    2022-10-10
  • React服務(wù)端渲染原理解析與實(shí)踐

    React服務(wù)端渲染原理解析與實(shí)踐

    這篇文章主要介紹了React服務(wù)端渲染原理解析與實(shí)踐,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-03-03
  • react18?hooks自定義移動端Popup彈窗組件RcPop

    react18?hooks自定義移動端Popup彈窗組件RcPop

    這篇文章主要介紹了react18?hooks自定義移動端Popup彈窗組件RcPop,react-popup?基于react18+hook自定義多功能彈框組件,整合了msg/alert/dialog/toast及android/ios彈窗效果,需要的朋友可以參考下
    2023-08-08
  • react自適應(yīng)布局px轉(zhuǎn)rem實(shí)現(xiàn)示例詳解

    react自適應(yīng)布局px轉(zhuǎn)rem實(shí)現(xiàn)示例詳解

    這篇文章主要為大家介紹了react自適應(yīng)布局px轉(zhuǎn)rem實(shí)現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-08-08
  • Remix集成antd和pro-components的過程示例

    Remix集成antd和pro-components的過程示例

    這篇文章主要為大家介紹了Remix集成antd和pro-components的過程示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-03-03

最新評論

康定县| 石门县| 登封市| 彭水| 衡阳县| 察雅县| 册亨县| 个旧市| 贵州省| 平凉市| 盐池县| 张家界市| 司法| 三江| 黔江区| 广州市| 富裕县| 桃园市| 杭锦旗| 龙里县| 武陟县| 昌平区| 台南市| 河池市| 稷山县| 博白县| 苗栗市| 四川省| 宁津县| 诏安县| 徐水县| 宜春市| 曲松县| 通化市| 宁远县| 武强县| 苍山县| 红原县| 班戈县| 英超| 阜新市|