如何在React中优化缓存的方法(详细指南)

如何在React中优化缓存的方法(详细指南)

文章图片
React优化缓存实例教程
作为用于创建高性能 Web 应用程序的最受欢迎的前端库之一,React 遵循基于组件的方法,其中每个组件都有自己的状态和逻辑。
如何在React中优化缓存?React 面临的最大挑战是避免不必要的渲染,这会导致严重的性能问题,尤其是在大型应用程序中。在本文中,我们将介绍几种不同的方法,通过不同的缓存方法来优化 React 应用程序的性能。
React优化缓存的方法:用于记忆的 React Hooks记忆(Memoization)是 React 本身提供的一个特性。正如我们所知,React 每次重新渲染时都会创建新的引用。如果你的组件有大量计算,即使输出没有改变,也会在每次重新渲染时进行计算。
为了通过避免不必要的负载来使 CPU 负载最小化,React 提供了两个有助于记忆的 Hook。Hooks 遵循一个过程,其中结果被缓存在内存中,当我们得到相同的输入时,无需重新计算就返回。在不同输入的情况下,缓存失效。
useMemo()
React优化缓存实例教程:useMemo()是 React 提供的用于记忆的 Hook,有助于保持缓存值与提供给它的值相同。它跟踪输入并返回先前执行的结果。
让我们看一个例子。假设我们必须在具有以下功能的组件中添加两个巨大的数字:
const addTwoHugeNumbers=(a,b)=>{ return a+b }

上面写的函数对 CPU 来说很重,因此应该只在a和的值b改变时计算。但是,默认情况下,它将在每次重新渲染时运行。
使用useMemo(),我们可以存储特定值的结果,这意味着函数不会计算,我们将直接获得先前计算的结果:
const memoizedValue = https://www.lsbin.com/useMemo(() => addTwoHugeNumbers(a, b), [ a, b])

该值存储在memoizedValue.  我们已经将依赖数组传递给useMemo,它告诉它什么时候再次运行。在我们的例子中,它会在任何一个值改变时运行。
UseCallback()
使用useCallback(),我们也获得了记忆的能力,但它以不同的方式工作。useCallback()不记忆值,而是记忆提供给它的回调函数。让我们看一个小例子:
const increment = (() => { setCount(count + 1); });

使用useCallback(),上面的函数类似于下面的代码:
const increment = useCallback(() => { setCount(count + 1); }, [ count]);

useCallback()将记住增量函数,仅在给定的依赖项发生变化时运行。它不跟踪输入或函数返回的值。
延迟加载 React 组件如何在React中优化缓存?React 中的延迟加载会预先呈现必要的组件,并将加载不重要的组件延迟到之后。
特别是在较大的应用程序中,强烈建议使用这种方法来提高性能。在 React 中,我们有内置选项来延迟加载组件。
我们已经创建了一个名为的组件< /Artists> ,我们希望它延迟加载,我们可以这样做:
import { lazy } from 'react';

首先,我们从 react 中导入 lazy 并使用它,如下所示:
const Artists = React.lazy(() => import('./Artists')); function App() { return ( < div> < Artists /> < /div> ); }

useRef()
React优化缓存的方法:我们知道,无论何时在组件中使用useState(),当状态改变时,它都会在组件中重新呈现。为了跟踪状态而不引起重新呈现,React引入了useRef()钩子。
在某些情况下,useState()可能不是您的应用程序的正确解决方案。useRef()非常适合于这样的情况:我们需要的状态不会导致重新呈现,并且对组件呈现的可见信息没有贡献。例如,你可以用它来计数渲染:
function App() { const [ foo, setFoo] = React.useState(false) const counter = React.useRef(0) console.log(counter.current++) return ( < button onClick={() => setFoo(f => !f)} > Click < /button> ) }ReactDOM.render(< React.StrictMode>< App />< /React.StrictMode>, document.getElementById('mydiv'))

在上面的代码中,我们有一个简单的切换器,用于重新呈现组件。Counter是一个持久化其值的可变ref。我们可以对useState()做同样的事情,但它会为每个切换导致两次呈现。
React优化缓存实例教程:Redux 缓存选择器选择器只是用于从更大的数据池中选择数据的函数。在 React 中,选择器被广泛用于从 Redux 存储中获取值。选择器非常有用和强大,但它们也有自己的缺点。
在React Redux中,我们有useSelector()钩子,用于从商店获取状态。useSelector()的问题在于它在组件每次呈现时都会运行。useSelector()在某些情况下可能是理想的,但大多数情况下,选择器返回的数据不会改变,这使得不必要的计算。
让我们看一个例子:
import React, {useEffect,useState} from 'react' import {useSelector, useDispatch} from 'react-redux' import {getPosts} from './postActions'export const List=()=>{ Const [ toggle, setToggle]=useState(false) const myPosts=useSelector(state=>state.posts) const dispatch=useDispatch()return( < div> {myPosts.map(post=>< p>{posts}< p/>)} < button type="button" onClick={()=>{setToggle(!toggle)}} >Click Me!< /button> < div/> ) }

在上面的代码中,我们正在更改切换状态,并且每次我们执行此操作时组件都会呈现。该挂钩也将运行,即使职位不符合我们的终极版店内改变。useSelector()
为了解决这个问题,我们将缓存一个选择器函数的结果。尽管没有内置的 React 解决方案,但我们有许多第三方库允许我们创建缓存选择器。让我们使用 Reselect,这是缓存选择器的著名解决方案。
Reselect
React优化缓存的方法:Reselect 是一个流行的库,用于创建记忆化选择器。你可以使用以下命令将其安装到你的项目中:
yarn add reselect

我们可以使用 Reselect 如下:
import { createSelector } from 'reselect' import React, {useEffect,useState} from 'react' import {useSelector, useDispatch} from 'react-redux' import {getPosts} from './postActions'export const List=()=>{ Const [ toggle, setToggle]=useState(false) const myPosts = createSelector(state=>state.posts) const dispatch=useDispatch()return( < div> {myPosts.map(post=>< p>{posts}< p/>)} < button type="button" onClick={()=>{setToggle(!toggle)}} >Click Me!< /button> < div/> ) }

在上面的代码中,我们createSelector从 Reselect导入,它接受一个选择器并返回它的记忆版本。使用记忆化版本,即使经过数千次重新渲染,组件也不会计算选择器的值,除非值发生postReducer变化。createSelector事实证明,Reselect 是解决大型应用程序性能问题的绝佳解决方案。
使用 React Query 优化 API 调用如何在React中优化缓存?React 以自己的方式处理异步操作,这有时是开发人员的一个问题。异步操作的常用模式是在useEffectHook 中获取服务器数据,它在每次渲染时运行并每次获取新数据,即使服务器上没有新数据。
另一方面,React Query 缓存数据并在调用之前先返回它,但是如果服务器返回的新数据与之前的数据相同,React Query 将不会重新渲染组件。我们可以使用 React Query 如下:
import React from 'react' import {useQuery} from 'react-query' import axios from 'axios'async function fetchPosts(){ const {data} = await axios.get('https://jsonplaceholder.typicode.com/posts') return data }function Posts(){ const {data, error, isError, isLoading } = useQuery('posts', fetchPosts) // first argument is a string to cache and track the query result if(isLoading){ return < div>Loading...< /div> } if(isError){ return < div>Error! {error.message}< /div> }return( < div className='container'> < h1>Posts< /h1> { data.map((post, index) => { return < li key={index}>{post.title}< /li> }) }< /div> ) }export default Posts

React片段React优化缓存实例教程:如果你是 React 开发人员,你可能遇到过一个错误,提示将组件与父 div 包装在一起。如果你的组件中不需要额外的 div,则添加它没有意义。例如,如果你的 React 应用程序中有 1000 个组件,那么你将有 1000 个额外的 div,这对 DOM 来说可能很重。为了避免这种情况,React 为你提供了使用片段的选项:
const Message = () => { return ( < React.Fragment> < p>Hello< p/> < p>I have message for you< p/> < /React.Fragment> ); };

下面的代码片段与上面的代码完全相同,< > 用作React.Fragment的快捷方式:
const Message = () => { return ( < > < p>Hello< p/> < p>I have message for you< p/> < /> ); };

无论使用哪种方法,都可以避免添加额外的< div> ,从而减少 DOM 标记、提高渲染性能并减少内存开销。
React虚拟列表如何在React中优化缓存?通常,我们需要在浏览器上呈现大型列表;这样做对浏览器来说是很复杂的,因为它必须创建新节点并将它们全部绘制在屏幕上。
为了使 React 中的过程高效,我们可以选择使用虚拟列表。虚拟列表仅根据需要呈现少数项目,只需在用户动态滚动项目时替换它们。
渲染比更改 DOM 更快,因此你可以使用虚拟列表以快速的性能渲染数千个列表项。React-virtualized是一个优秀的库,它具有渲染虚拟列表的组件。
React优化缓存的方法:功能组件React 从基于类的组件开始,但是,由于其轻量级的特性,现在建议使用函数式组件。功能组件基本上是创建速度更快的函数,并且它们更容易缩小,从而减小包的大小。
React优化缓存实例教程结论在本教程中,我们介绍了几种用于优化 React 应用程序中缓存管理的不同解决方案,例如记忆、缓存选择器、延迟加载、React 片段、虚拟列表和功能组件。这些方法中的每一种都可以通过减少不必要的组件渲染数量、减少开销和提高速度来改进你的应用程序。
【如何在React中优化缓存的方法(详细指南)】正确的解决方案将取决于你个人项目的需求,但希望本文能帮助你了解可用的选项。

    推荐阅读