当前位置: 首页 > news >正文

如何使用usememo和usecallback进行性能优化,什么时候使用usecallback,什么时候使用usememo

React useMemo 和 useCallback 性能优化总结以及使用场景

基本概念

useMemo

用于缓存计算结果,避免在每次渲染时重复进行昂贵的计算。

useCallback

用于缓存函数引用,避免在每次渲染时创建新的函数引用。

使用时机对比

useMemo 适用场景

  1. 复杂计算
function DataGrid({ items, filter }) {// 适用:复杂的数据处理const filteredItems = useMemo(() => {return items.filter(item => {return complexFilterLogic(item, filter);});}, [items, filter]);return <div>{filteredItems.map(item => <Item key={item.id} {...item} />)}</div>;
}
  1. 避免重复创建大对象
function ChartComponent({ data }) {// 适用:大数据结构转换const chartConfig = useMemo(() => ({data: transformData(data),options: {// 复杂的配置对象animations: { ... },scales: { ... },plugins: { ... }}}), [data]);return <Chart config={chartConfig} />;
}
  1. 引用相等性重要的场景
function ParentComponent() {// 适用:作为 props 传递的对象const memoizedValue = useMemo(() => ({id: 'unique',data: expensiveComputation()}), []);return <ChildComponent config={memoizedValue} />;
}

useCallback 适用场景

  1. 传递给子组件的回调函数
function ParentComponent() {const [items, setItems] = useState([]);// 适用:传递给子组件的事件处理函数const handleDelete = useCallback((id: string) => {setItems(prev => prev.filter(item => item.id !== id));}, []); // 依赖为空因为不依赖任何外部变量return <ItemList items={items} onDelete={handleDelete} />;
}
  1. 自定义 Hook 中返回的函数
function useSearch(initialQuery: string) {const [query, setQuery] = useState(initialQuery);// 适用:Hook 返回的函数const search = useCallback(async () => {const results = await api.search(query);return results;}, [query]);return { search, query, setQuery };
}
  1. 依赖于 props 或状态的事件处理
function UserActions({ userId, onSuccess }) {// 适用:依赖外部变量的回调const handleUpdate = useCallback(async (data) => {await api.updateUser(userId, data);onSuccess();}, [userId, onSuccess]);return <UserForm onSubmit={handleUpdate} />;
}

不需要使用的场景

不需要 useMemo

  1. 简单的计算
// ❌ 过度优化
const fullName = useMemo(() => firstName + ' ' + lastName, [firstName, lastName]
);// ✅ 直接计算
const fullName = firstName + ' ' + lastName;
  1. 基本类型值
// ❌ 不必要
const count = useMemo(() => items.length, [items]);// ✅ 直接使用
const count = items.length;

不需要 useCallback

  1. 组件内部使用的函数
// ❌ 不必要
const handleClick = useCallback(() => {console.log('clicked');
}, []);// ✅ 直接定义
const handleClick = () => {console.log('clicked');
};
  1. 不会作为 props 传递的函数
// ❌ 过度优化
const formatDate = useCallback((date) => {return new Date(date).toLocaleDateString();
}, []);// ✅ 直接定义或移到组件外
const formatDate = (date) => {return new Date(date).toLocaleDateString();
};

最佳实践

  1. 合理使用依赖数组
function SearchComponent({ onSearch }) {const [query, setQuery] = useState('');const handleSearch = useCallback(() => {onSearch(query);}, [query, onSearch]); // 包含所有依赖项
}
  1. 配合 React.memo 使用
const MemoizedChild = React.memo(function Child({ onAction }) {return <button onClick={onAction}>Click me</button>;
});function Parent() {const handleAction = useCallback(() => {// 处理逻辑}, []); // 空依赖数组确保函数引用稳定return <MemoizedChild onAction={handleAction} />;
}
  1. 避免过度优化
function App() {// 只在真正需要的地方使用const expensiveValue = useMemo(() => veryExpensiveOperation(), [/* 相关依赖 */]);const criticalCallback = useCallback(() => importantOperation(), [/* 相关依赖 */]);
}

性能考虑

  1. 监控性能影响
  • 使用 React DevTools Profiler
  • 测量实际性能提升
  • 只在有明显收益时使用
  1. 权衡成本
  • 考虑内存使用
  • 评估缓存开销
  • 注意依赖数组的大小
  1. 优化策略
  • 优先考虑架构优化
  • 合理拆分组件
  • 使用适当的数据结构

相关文章:

如何使用usememo和usecallback进行性能优化,什么时候使用usecallback,什么时候使用usememo

React useMemo 和 useCallback 性能优化总结以及使用场景 基本概念 useMemo 用于缓存计算结果&#xff0c;避免在每次渲染时重复进行昂贵的计算。 useCallback 用于缓存函数引用&#xff0c;避免在每次渲染时创建新的函数引用。 使用时机对比 useMemo 适用场景 复杂计算…...

22. C语言 输入与输出详解

本章目录: 前言1. 输入输出的基础概念1.1 标准输入输出流1.2 输入输出函数 2. 格式化输出与输入2.1 使用 printf() 进行输出示例 1: 输出字符串示例 2: 输出整数示例 3: 输出浮点数 2.2 使用 scanf() 进行输入示例 4: 读取整数和字符改进方案&#xff1a;使用getchar()清理缓冲…...

WPF实战案例 | C# WPF实现计算器源码

WPF实战案例 | C# WPF实现计算器源码 一、设计来源计算器应用程序讲解1.1 主界面1.2 计算界面 二、效果和源码2.1 界面设计&#xff08;XAML&#xff09;2.2 代码逻辑&#xff08;C#&#xff09;2.3 实现步骤总结 源码下载更多优质源码分享 作者&#xff1a;xcLeigh 文章地址&a…...

AutoGen入门——快速实现多角色、多用户、多智能体对话系统

1.前言 如https://github.com/microsoft/autogen所述&#xff0c;autogen是一多智能体的框架&#xff0c;属于微软旗下的产品。 依靠AutoGen我们可以快速构建出一个多智能体应用&#xff0c;以满足我们各种业务场景。 本文将以几个示例场景&#xff0c;使用AutoGen快速构建出…...

LeetCode 热题 100_全排列(55_46_中等_C++)(递归(回溯))

LeetCode 热题 100_两数之和&#xff08;55_46&#xff09; 题目描述&#xff1a;输入输出样例&#xff1a;题解&#xff1a;解题思路&#xff1a;思路一&#xff08;递归&#xff08;回溯&#xff09;&#xff09;&#xff1a; 代码实现代码实现&#xff08;思路一&#xff08…...

将 AzureBlob 的日志通过 Azure Event Hubs 发给 Elasticsearch(1.标准版)

问题 项目里使用了 AzureBlob 存储了用户上传的各种资源文件&#xff0c;近期 AzureBlob 的流量费用增长很快&#xff0c;想通过分析Blob的日志&#xff0c;获取一些可用的信息&#xff0c;所以有了这个需求&#xff1a;将存储账户的日志&#xff08;读写&#xff0c;审计&…...

pthread_exit函数

pthread_exit 是 POSIX 线程库&#xff08;pthread&#xff09;中的一个函数&#xff0c;用于显式地终止调用线程。与 exit 函数不同&#xff0c;pthread_exit 仅影响调用它的线程&#xff0c;而不是整个进程。使用 pthread_exit 可以确保线程在退出时能够正确地释放线程相关的…...

1月21日星期二今日早报简报微语报早读

1月21日星期二&#xff0c;农历腊月廿二&#xff0c;早报#微语早读。 1、多地官宣&#xff1a;2025年可有序、限时或在限定区域燃放烟花爆竹&#xff1b; 2、TikTok恢复在美服务&#xff1b;特朗普提出继续运营TikTok方案&#xff0c;外交部&#xff1a;若涉及收购中国企业应…...

【2024年终总结】我与CSDN的一年

&#x1f449;作者主页&#xff1a;心疼你的一切 &#x1f449;作者简介&#xff1a;大家好,我是心疼你的一切。Unity3D领域新星创作者&#x1f3c6;&#xff0c;华为云享专家&#x1f3c6; &#x1f449;记得点赞 &#x1f44d; 收藏 ⭐爱你们&#xff0c;么么哒 文章目录 …...

openssl 正确生成v3带SAN的证书

初级代码游戏的专栏介绍与文章目录-CSDN博客 我的github&#xff1a;codetoys&#xff0c;所有代码都将会位于ctfc库中。已经放入库中我会指出在库中的位置。 这些代码大部分以Linux为目标但部分代码是纯C的&#xff0c;可以在任何平台上使用。 源码指引&#xff1a;github源…...

Golang Gin系列-5:数据模型和数据库

在这篇Gin教程的博客中&#xff0c;我们将探索如何将模型和数据库与Gin框架无缝集成&#xff0c;使你能够构建健壮且可扩展的web应用程序。通过利用流行的库并遵循最佳实践&#xff0c;你将学习如何定义模型、建立数据库连接、执行CRUD操作以及确保基于gin的项目中的数据完整性…...

比简单工厂更好的 - 工厂方法模式(Factory Method Pattern)

工厂方法模式&#xff08;Factory Method Pattern&#xff09; 工厂方法模式&#xff08;Factory Method Pattern&#xff09;工厂方法模式&#xff08;Factory Method Pattern&#xff09;概述工厂方法模式&#xff08;Factory Method Pattern&#xff09;结构图工厂方法模式&…...

分布式搜索引擎02

1. DSL查询文档 elasticsearch的查询依然是基于JSON风格的DSL来实现的。 1.1. DSL查询分类 Elasticsearch提供了基于JSON的DSL&#xff08;Domain Specific Language&#xff09;来定义查询。常见的查询类型包括&#xff1a; 查询所有&#xff1a;查询出所有数据&#xff0c…...

阿里云安装mikrotik7配置内网互通

阿里云近期推出了200M不限量机器&#xff0c;对于没有公网接入的中小企业可以借助这个机器对多地分支机构进行内网互通。目前已经有很多机构用这个搞跨云k8s,跨云集群了。 mikrotik作为一个商用的软件&#xff0c;操作性比一些开源的软件好用不少。 本文使用的网段为172.16.1…...

Docker网段和服务器ip冲突导致无法访问网络的解决方法

若宿主机所在网络的网段为172.[17-31].xx.xx&#xff0c;则会与Docker本身内部网络间出现冲突&#xff0c;此时需要重新配置Docker默认地址池 一&#xff1a;查看docker的默认网段 route 二&#xff1a;修改docker的默认网段 etc/docker/daemon.json文件增加修改网段信息 {…...

Kubernetes 集群中安装和配置 Kubernetes Dashboard

前言 上篇成功部署Kubernetes集群后&#xff0c;为了方便管理和监控集群资源&#xff0c;安装Kubernetes Dashboard显得尤为重要。Kubernetes Dashboard 是一个通用的、基于 Web 的 UI&#xff0c;旨在让用户轻松地部署容器化应用到 Kubernetes 集群&#xff0c;并对这些应用进…...

Android开发之Spinner

Android开发之Spinner 1. 概述2. Spinner3. 适配器3.1 ArrayAdapter3.2 SimpleAdapter 1. 概述 Android开发学习笔记。学习下拉框控件Spinner和适配器&#xff08;数组适配器ArrayAdapter、简单适配器SimpleAdapter&#xff09;的使用。 2. Spinner 下拉框控件&#xff0c;用…...

【c++继承篇】--继承之道:在C++的世界中编织血脉与传承

目录 引言 一、定义二、继承定义格式2.1定义格式2.2继承关系和访问限定符2.3继承后子类访问权限 三、基类和派生类赋值转换四、继承的作用域4.1同名变量4.2同名函数 五、派生类的默认成员构造函数5.1**构造函数调用顺序&#xff1a;**5.2**析构函数调用顺序&#xff1a;**5.3调…...

分布式系统通信解决方案:Netty 与 Protobuf 高效应用

分布式系统通信解决方案&#xff1a;Netty 与 Protobuf 高效应用 一、引言 在现代网络编程中&#xff0c;数据的编解码是系统设计的一个核心问题&#xff0c;特别是在高并发和低延迟的应用场景中&#xff0c;如何高效地序列化和传输数据对于系统的性能至关重要。随着分布式系…...

计算机网络 (54)系统安全:防火墙与入侵检测

前言 计算机网络系统安全是确保网络通信和数据不受未经授权访问、泄露、破坏或篡改的关键。防火墙和入侵检测系统&#xff08;IDS&#xff09;是维护网络系统安全的两大核心组件。 一、防火墙 定义与功能 防火墙是一种用来加强网络之间访问控制的特殊网络互联设备&#xff0c;它…...

关于nvm与node.js

1 安装nvm 安装过程中手动修改 nvm的安装路径&#xff0c; 以及修改 通过nvm安装node后正在使用的node的存放目录【这句话可能难以理解&#xff0c;但接着往下看你就了然了】 2 修改nvm中settings.txt文件配置 nvm安装成功后&#xff0c;通常在该文件中会出现以下配置&…...

SpringBoot+uniapp 的 Champion 俱乐部微信小程序设计与实现,论文初版实现

摘要 本论文旨在设计并实现基于 SpringBoot 和 uniapp 的 Champion 俱乐部微信小程序&#xff0c;以满足俱乐部线上活动推广、会员管理、社交互动等需求。通过 SpringBoot 搭建后端服务&#xff0c;提供稳定高效的数据处理与业务逻辑支持&#xff1b;利用 uniapp 实现跨平台前…...

微服务商城-商品微服务

数据表 CREATE TABLE product (id bigint(20) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT 商品id,cateid smallint(6) UNSIGNED NOT NULL DEFAULT 0 COMMENT 类别Id,name varchar(100) NOT NULL DEFAULT COMMENT 商品名称,subtitle varchar(200) NOT NULL DEFAULT COMMENT 商…...

C++ 求圆面积的程序(Program to find area of a circle)

给定半径r&#xff0c;求圆的面积。圆的面积应精确到小数点后5位。 例子&#xff1a; 输入&#xff1a;r 5 输出&#xff1a;78.53982 解释&#xff1a;由于面积 PI * r * r 3.14159265358979323846 * 5 * 5 78.53982&#xff0c;因为我们只保留小数点后 5 位数字。 输…...

在鸿蒙HarmonyOS 5中使用DevEco Studio实现录音机应用

1. 项目配置与权限设置 1.1 配置module.json5 {"module": {"requestPermissions": [{"name": "ohos.permission.MICROPHONE","reason": "录音需要麦克风权限"},{"name": "ohos.permission.WRITE…...

精益数据分析(97/126):邮件营销与用户参与度的关键指标优化指南

精益数据分析&#xff08;97/126&#xff09;&#xff1a;邮件营销与用户参与度的关键指标优化指南 在数字化营销时代&#xff0c;邮件列表效度、用户参与度和网站性能等指标往往决定着创业公司的增长成败。今天&#xff0c;我们将深入解析邮件打开率、网站可用性、页面参与时…...

Xen Server服务器释放磁盘空间

disk.sh #!/bin/bashcd /run/sr-mount/e54f0646-ae11-0457-b64f-eba4673b824c # 全部虚拟机物理磁盘文件存储 a$(ls -l | awk {print $NF} | cut -d. -f1) # 使用中的虚拟机物理磁盘文件 b$(xe vm-disk-list --multiple | grep uuid | awk {print $NF})printf "%s\n"…...

iOS性能调优实战:借助克魔(KeyMob)与常用工具深度洞察App瓶颈

在日常iOS开发过程中&#xff0c;性能问题往往是最令人头疼的一类Bug。尤其是在App上线前的压测阶段或是处理用户反馈的高发期&#xff0c;开发者往往需要面对卡顿、崩溃、能耗异常、日志混乱等一系列问题。这些问题表面上看似偶发&#xff0c;但背后往往隐藏着系统资源调度不当…...

七、数据库的完整性

七、数据库的完整性 主要内容 7.1 数据库的完整性概述 7.2 实体完整性 7.3 参照完整性 7.4 用户定义的完整性 7.5 触发器 7.6 SQL Server中数据库完整性的实现 7.7 小结 7.1 数据库的完整性概述 数据库完整性的含义 正确性 指数据的合法性 有效性 指数据是否属于所定…...

C# 表达式和运算符(求值顺序)

求值顺序 表达式可以由许多嵌套的子表达式构成。子表达式的求值顺序可以使表达式的最终值发生 变化。 例如&#xff0c;已知表达式3*52&#xff0c;依照子表达式的求值顺序&#xff0c;有两种可能的结果&#xff0c;如图9-3所示。 如果乘法先执行&#xff0c;结果是17。如果5…...