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

淺談React useTransition并發(fā)特性

 更新時間:2026年05月13日 08:16:11   作者:兆子龍  
本文主要介紹了React的useTransition Hook,它可以幫助開發(fā)者將某些狀態(tài)更新標(biāo)記為“非緊急”,從而優(yōu)化用戶體驗,并提供了注意事項和性能優(yōu)化建議,感興趣的可以了解一下

一、為什么需要 useTransition

在 React 中,所有狀態(tài)更新默認(rèn)都是緊急的,會立即阻塞 UI。

function SearchPage() {
  const [query, setQuery] = useState('');
  const [results, setResults] = useState([]);
  const handleChange = (e) => {
    const value = e.target.value;
    setQuery(value);  // 緊急更新
    // 耗時的過濾操作
    const filtered = hugeList.filter(item => 
      item.name.includes(value)
    );
    setResults(filtered);  // 也是緊急更新,會卡頓
  };
  return (
    <>
      <input value={query} onChange={handleChange} />
      <Results data={results} />
    </>
  );
}

問題:輸入時會卡頓,因為每次輸入都要等待過濾完成。

二、useTransition 的解決方案

useTransition 可以將某些更新標(biāo)記為"非緊急",讓 React 優(yōu)先處理用戶交互。

import { useState, useTransition } from 'react';

function SearchPage() {
  const [query, setQuery] = useState('');
  const [results, setResults] = useState([]);
  const [isPending, startTransition] = useTransition();

  const handleChange = (e) => {
    const value = e.target.value;
    setQuery(value);  // 緊急更新,立即響應(yīng)
    
    startTransition(() => {
      // 非緊急更新,可以被打斷
      const filtered = hugeList.filter(item => 
        item.name.includes(value)
      );
      setResults(filtered);
    });
  };

  return (
    <>
      <input value={query} onChange={handleChange} />
      {isPending && <Spinner />}
      <Results data={results} />
    </>
  );
}

效果:輸入流暢,過濾操作在后臺進(jìn)行。

三、核心概念

返回值

const [isPending, startTransition] = useTransition();
  • isPending: 是否有待處理的 transition
  • startTransition: 將更新標(biāo)記為 transition

緊急 vs 非緊急更新

// 緊急更新:立即執(zhí)行,不可打斷
setQuery(value);

// 非緊急更新:可以被打斷,延遲執(zhí)行
startTransition(() => {
  setResults(filtered);
});

四、實戰(zhàn)場景

場景 1:搜索過濾

function ProductList() {
  const [searchTerm, setSearchTerm] = useState('');
  const [filteredProducts, setFilteredProducts] = useState(products);
  const [isPending, startTransition] = useTransition();

  const handleSearch = (value) => {
    setSearchTerm(value);
    
    startTransition(() => {
      const filtered = products.filter(p =>
        p.name.toLowerCase().includes(value.toLowerCase())
      );
      setFilteredProducts(filtered);
    });
  };

  return (
    <>
      <input
        value={searchTerm}
        onChange={e => handleSearch(e.target.value)}
        placeholder="搜索商品..."
      />
      {isPending && <div className="loading">搜索中...</div>}
      <div className="products">
        {filteredProducts.map(p => (
          <ProductCard key={p.id} {...p} />
        ))}
      </div>
    </>
  );
}

場景 2:Tab 切換

function TabContainer() {
  const [tab, setTab] = useState('home');
  const [isPending, startTransition] = useTransition();

  const handleTabChange = (newTab) => {
    startTransition(() => {
      setTab(newTab);  // 切換 tab 是非緊急的
    });
  };

  return (
    <>
      <div className="tabs">
        <button
          onClick={() => handleTabChange('home')}
          className={tab === 'home' ? 'active' : ''}
        >
          首頁
        </button>
        <button
          onClick={() => handleTabChange('profile')}
          className={tab === 'profile' ? 'active' : ''}
        >
          個人中心
        </button>
      </div>
      
      {isPending && <LoadingBar />}
      
      <div className="tab-content">
        {tab === 'home' && <HomePage />}
        {tab === 'profile' && <ProfilePage />}
      </div>
    </>
  );
}

場景 3:路由切換

function App() {
  const [page, setPage] = useState('home');
  const [isPending, startTransition] = useTransition();

  const navigate = (newPage) => {
    startTransition(() => {
      setPage(newPage);
    });
  };

  return (
    <>
      <nav>
        <button onClick={() => navigate('home')}>首頁</button>
        <button onClick={() => navigate('about')}>關(guān)于</button>
        <button onClick={() => navigate('contact')}>聯(lián)系</button>
      </nav>
      
      {isPending && <TopLoadingBar />}
      
      <main>
        {page === 'home' && <Home />}
        {page === 'about' && <About />}
        {page === 'contact' && <Contact />}
      </main>
    </>
  );
}

五、與 useDeferredValue 對比

// useTransition:主動標(biāo)記更新
const [isPending, startTransition] = useTransition();
startTransition(() => {
  setValue(newValue);
});

// useDeferredValue:被動延遲值
const deferredValue = useDeferredValue(value);
特性useTransitionuseDeferredValue
使用方式包裹更新函數(shù)包裹值
控制權(quán)主動控制被動延遲
isPending
適用場景控制更新時機(jī)延遲渲染

六、注意事項

1. 只能在 transition 中更新 state

// ? 正確
startTransition(() => {
  setState(newValue);
});

// ? 錯誤:不能包含異步操作
startTransition(async () => {
  const data = await fetchData();
  setState(data);
});

2. 異步操作需要特殊處理

const handleClick = async () => {
  const data = await fetchData();
  
  startTransition(() => {
    setState(data);  // 只有 setState 在 transition 中
  });
};

3. 不要過度使用

// ? 不需要:簡單的狀態(tài)更新
startTransition(() => {
  setCount(count + 1);
});

// ? 需要:耗時的計算或渲染
startTransition(() => {
  setResults(expensiveFilter(data));
});

七、性能優(yōu)化

配合 memo 使用

const ExpensiveList = memo(({ items }) => {
  return items.map(item => <ExpensiveItem key={item.id} {...item} />);
});

function App() {
  const [query, setQuery] = useState('');
  const [items, setItems] = useState(allItems);
  const [isPending, startTransition] = useTransition();

  const handleSearch = (value) => {
    setQuery(value);
    startTransition(() => {
      setItems(allItems.filter(i => i.name.includes(value)));
    });
  };

  return (
    <>
      <input value={query} onChange={e => handleSearch(e.target.value)} />
      {isPending && <Spinner />}
      <ExpensiveList items={items} />
    </>
  );
}

八、與 Suspense 配合

function App() {
  const [tab, setTab] = useState('home');
  const [isPending, startTransition] = useTransition();

  return (
    <>
      <Tabs value={tab} onChange={(t) => {
        startTransition(() => setTab(t));
      }} />
      
      <Suspense fallback={<Skeleton />}>
        {isPending && <InlineSpinner />}
        {tab === 'home' && <Home />}
        {tab === 'posts' && <Posts />}
      </Suspense>
    </>
  );
}

到此這篇關(guān)于淺談React useTransition并發(fā)特性的文章就介紹到這了,更多相關(guān)React useTransition并發(fā)內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 關(guān)于useEffect的第二個參數(shù)解讀

    關(guān)于useEffect的第二個參數(shù)解讀

    這篇文章主要介紹了關(guān)于useEffect的第二個參數(shù),具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-09-09
  • React簡介入門教程

    React簡介入門教程

    本文總結(jié)了React的基礎(chǔ)知識點,包括環(huán)境搭建、核心概念(JSX、組件、props、state、事件處理、條件渲染、列表渲染)以及組件進(jìn)階(生命周期、Hooks、通信),適合零基礎(chǔ)開發(fā)者學(xué)習(xí),涵蓋理論與實操,適合React項目的開發(fā)和維護(hù),感興趣的朋友跟隨小編一起看看吧
    2026-02-02
  • React?split實現(xiàn)分割字符串的使用示例

    React?split實現(xiàn)分割字符串的使用示例

    當(dāng)我們需要將一個字符串按照指定的分隔符進(jìn)行分割成數(shù)組時,我們可以在組件的生命周期方法中使用split方法來實現(xiàn)這個功能,本文就來介紹一下,感興趣的可以了解下
    2023-10-10
  • React?Flux與Redux設(shè)計及使用原理

    React?Flux與Redux設(shè)計及使用原理

    這篇文章主要介紹了React?Flux與Redux設(shè)計及使用,Redux最主要是用作應(yīng)用狀態(tài)的管理。簡言之,Redux用一個單獨的常量狀態(tài)樹(state對象)保存這一整個應(yīng)用的狀態(tài),這個對象不能直接被改變
    2023-03-03
  • react 報錯Module build failed: BrowserslistError: Unknown browser query `dead`問題的解決方法

    react 報錯Module build failed: Browserslis

    這篇文章主要介紹了react 報錯Module build failed: BrowserslistError: Unknown browser query `dead`問題的解決方法,需要的朋友可以參考下
    2023-06-06
  • React?記憶緩存的三種方法實現(xiàn)

    React?記憶緩存的三種方法實現(xiàn)

    本文主要介紹了React?記憶緩存的三種方法實現(xiàn),包含React.memo、useMemo、useCallback,用于避免不必要的組件重渲染和計算,感興趣的可以了解一下
    2025-09-09
  • 歸納總結(jié)Remix?表單常用方法及示例詳解

    歸納總結(jié)Remix?表單常用方法及示例詳解

    這篇文章主要為大家歸納總結(jié)了Remix?表單常用方法及示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-03-03
  • 從源碼到架構(gòu):React?useActionState?深度解析

    從源碼到架構(gòu):React?useActionState?深度解析

    React 19引入的 useActionState是近年來React Hooks 體系中設(shè)計最精巧的API 之一,本文給大家介紹從源碼到架構(gòu):React?useActionState?深度剖析,感興趣的朋友跟隨小編一起看看吧
    2026-05-05
  • react中用less的問題

    react中用less的問題

    本文主要介紹了react中用less的問題,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2024-04-04
  • 在react中使用 indexDb的方法

    在react中使用 indexDb的方法

    在React中使用IndexedDB進(jìn)行前端離線存儲,可以存儲大量數(shù)據(jù),支持復(fù)雜的數(shù)據(jù)類型和高性能查詢,通過示例展示了如何創(chuàng)建數(shù)據(jù)庫、添加數(shù)據(jù)、查詢數(shù)據(jù)和構(gòu)建一個簡單的待辦事項應(yīng)用,感興趣的朋友跟隨小編一起看看吧
    2024-11-11

最新評論

光山县| 广州市| 浑源县| 揭西县| 江川县| 镇坪县| 突泉县| 万全县| 墨玉县| 岳普湖县| 绥中县| 阳高县| 七台河市| 陵川县| 临漳县| 民勤县| 武乡县| 彝良县| 平潭县| 迁西县| 绥德县| 罗山县| 西丰县| 潼南县| 泰宁县| 利辛县| 措勤县| 汉中市| 政和县| 安康市| 丽水市| 文山县| 即墨市| 庄河市| 安化县| 五原县| 枣庄市| 彭水| 温州市| 肃南| 桦川县|