重生之我在chatgpt中学习React 第九天之懒加载(Lazy Loading)、性能分析(React Profiler)、 批量状态更新(Batching)-前端-E先生的博客
Java
MySQL
大数据
Python
前端
黑科技
大语言模型
    首页 >> 互联网 >> 前端

重生之我在chatgpt中学习React 第九天之懒加载(Lazy Loading)、性能分析(React Profiler)、 批量状态更新(Batching)

[导读]:React 学习指南 - 第九天 🚀今天,我们深入探讨 React 进阶优化技巧,包括 懒加载(Lazy Loading)、性能分析(React Profiler) 以及 批量状态更新(Batching)。这些技术可以帮助你优化应用性能,提升用户体验。1. 懒加载(Lazy Loading)懒加载是一种按需加载的技术,可以减少初始页面的加载时间,提高性能。1.1 React...

React 学习指南 - 第九天 🚀

今天,我们深入探讨 React 进阶优化技巧,包括 懒加载(Lazy Loading)性能分析(React Profiler) 以及 批量状态更新(Batching)。这些技术可以帮助你优化应用性能,提升用户体验


1. 懒加载(Lazy Loading)

懒加载是一种按需加载的技术,可以减少初始页面的加载时间,提高性能。

1.1 React 内置 React.lazy

React.lazy 允许我们按需动态加载组件,只有在组件渲染时才会加载相关代码。

import React, { Suspense, lazy } from 'react';

const LazyComponent = lazy(() => import('./LazyComponent'));

function App() {
  return (
    <div>
      <h2>Main Application</h2>
      <Suspense fallback={<h3>Loading...</h3>}>
        <LazyComponent />
      </Suspense>
    </div>
  );
}

export default App;

🔹 Suspense 作用
LazyComponent 还未加载完成时,会显示 fallback 组件(如 Loading...)。


1.2 懒加载路由

如果你的应用使用 React Router,可以对页面组件进行懒加载,提高首屏加载速度。

import React, { Suspense, lazy } from 'react';
import { BrowserRouter as Router, Route, Switch } from 'react-router-dom';

const Home = lazy(() => import('./Home'));
const About = lazy(() => import('./About'));

function App() {
  return (
    <Router>
      <Suspense fallback={<h3>Loading Page...</h3>}>
        <Switch>
          <Route path="/" exact component={Home} />
          <Route path="/about" component={About} />
        </Switch>
      </Suspense>
    </Router>
  );
}

export default App;

懒加载适用场景

  • 大型组件(例如富文本编辑器、图表库)

  • 低频访问的页面(如“关于我们”页面)

  • 仅在用户交互后才需要的功能(如模态框)


2. React Profiler(性能分析)

React Profiler 允许我们分析组件的渲染时间,帮助找出性能瓶颈。

2.1 如何使用 React Profiler

React DevTools 中,切换到 Profiler 选项卡,可以查看每个组件的渲染时间。


2.2 手动添加 Profiler 组件

如果想在代码中监测特定组件的性能,可以使用 Profiler 组件:

import React, { Profiler } from 'react';

function onRenderCallback(id, phase, actualDuration, baseDuration, startTime, commitTime) {
  console.log(`Component: ${id}`);
  console.log(`Phase: ${phase}`);
  console.log(`Render Time: ${actualDuration}ms`);
}

function ChildComponent() {
  return <h3>Hello, I'm a child component!</h3>;
}

function App() {
  return (
    <Profiler id="ChildComponent" onRender={onRenderCallback}>
      <ChildComponent />
    </Profiler>
  );
}

export default App;

🔹 Profiler 监测的信息:

  • id:组件名称

  • phase"mount"(初次渲染)或 "update"(重新渲染)

  • actualDuration:当前渲染所需时间

  • baseDuration:理想情况下的渲染时间

  • startTime / commitTime:渲染时间点


3. 批量状态更新(Batching)

React 18 之后,多个 setState 会自动合并,减少渲染次数,提高性能

3.1 React 18 以前的行为

在 React 17 及更早版本,在异步事件(如 setTimeout)中,setState 不是批量执行的

import React, { useState } from 'react';

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

  const handleClick = () => {
    setTimeout(() => {
      setCount(count + 1);
      setCount(count + 1);
      setCount(count + 1);
    }, 1000);
  };

  return (
    <div>
      <h2>Count: {count}</h2>
      <button onClick={handleClick}>Increment</button>
    </div>
  );
}

export default App;

🚨 问题: 即使 setCount(count + 1) 调用了 3 次,最终 count 只会增加 1。


3.2 React 18 的批量更新

在 React 18 及以后,setState 会在所有状态更新完成后再统一渲染

import React, { useState } from 'react';

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

  const handleClick = () => {
    setTimeout(() => {
      setCount((prev) => prev + 1);
      setCount((prev) => prev + 1);
      setCount((prev) => prev + 1);
    }, 1000);
  };

  return (
    <div>
      <h2>Count: {count}</h2>
      <button onClick={handleClick}>Increment</button>
    </div>
  );
}

export default App;

解决方案:使用 prevState 方式更新状态,避免竞态问题。


3.3 React flushSync 强制同步更新

如果你希望某些 setState 立即生效(不等到下一次批量更新),可以使用 flushSync

import { flushSync } from 'react-dom';

function handleClick() {
  flushSync(() => setCount(count + 1));
  console.log(count); // 立即更新
}

🔹 适用场景

  • 需要在 setState 之后立即获取最新的 state

  • 避免 UI 卡顿(如表单输入框)

🔹 明天预告React 服务器端渲染(SSR)和 Next.js! 🌍

image.png

本文来自E先生的博客,如若转载,请注明出处:https://javajz.cn

留言区

联系人:
手   机:
内   容:
验证码:

历史留言

欢迎加Easy的QQ