- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
从我从 React 文档和网络上的其他 Material 中了解到,useCallback 用于通过确保将回调的内存版本传递给子组件来避免重新渲染子组件,因此子组件的引用 props 保持不变。但这一切仅在我在子组件上使用 React.memo 时才有效。没有 React.memo,子组件无论如何都会重新渲染。我的问题是在这种情况下 useCallback 有什么用,即没有将 React.memo 应用于子组件。 useCallback 的其他好处是什么?
最佳答案
React.memo 确保在 props 进入组件时执行浅比较,并在它们相等时跳过组件的渲染。
给定一个子组件 Cell:
当应用于在渲染另一个父组件期间创建的功能组件时,将在每次渲染时创建一个新的 Cell 组件。这个新的 Cell 组件将始终对其 props 进行浅层比较,但它会在每次渲染其父级时重新渲染。
但是,如果它的依赖数组在父重新渲染期间没有更改,则 useCallback 将记住此函数回调 Cell。
单独一个包含在 useCallback 中的函数组件 Cell 在接收到 props 时将始终重新渲染,这将在其父级的每次渲染中发生。
然而不同的是,如果组件本身被重新创建,它的整个子树会被重新渲染,就像单独使用 React.memo 时的情况一样。
然而,配对在一起,您可以绕过重新渲染在父级内部定义的组件。
您会注意到,当尝试拖动 Memoized 单元格时,未包含在 useCallback 中的单元格不会发生拖动。这是因为当它的父元素重新渲染时,您尝试拖动的原始元素被重新创建为新实例。
更详细地解释了这个概念 here
示例
const { useCallback, useState, useRef } = React;
function App() {
const [state, setState] = useState(false);
const [title, setTitle] = useState("");
const Cell = useCallback(({ title }) => {
console.log(`${title} rendering`);
function onDragStart() {
setState(true);
}
function onDragEnd() {
setState(false);
}
return (
<div draggable onDragStart={onDragStart} onDragEnd={onDragEnd}>
Drag {title}
</div>
);
}, []);
const MemoizedCell = React.memo(({ title }) => {
console.log(`${title} rendering`);
function onDragStart() {
setState(true);
}
function onDragEnd() {
setState(false);
}
return (
<div draggable onDragStart={onDragStart} onDragEnd={onDragEnd}>
Drag {title}
</div>
);
});
const MemoizedCallbackCell = useCallback(
React.memo(({ title }) => {
console.log(`${title} rendering`);
function onDragStart() {
setState(true);
}
function onDragEnd() {
setState(false);
}
return (
<div draggable onDragStart={onDragStart} onDragEnd={onDragEnd}>
Drag {title}
<button onClick={() => setTitle(" Updated")}>Change Title</button>
</div>
);
}),
[]
);
return (
<div className="App">
<Cell title="Cell" />
<MemoizedCell title="Memoized Cell" />
<MemoizedCallbackCell title={"Memoized Callback Cell" + title} />
Is dragging {`${state}`}
<br />
</div>
);
}
ReactDOM.render(<App />, document.getElementById('root'));
关于javascript - 在没有 React.memo 的情况下使用 useCallback 有什么好处吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59663387/
我正在尝试通过容器将 Redux mapStateToProps() 和 mapActionCreators() 连接到登录屏幕,并且我正在使用 React 导航。 构建我的应用程序后,出现以下错误消
你能告诉我为什么我的标题每次渲染都已经使用了 React.memo 吗? 当我从 导航时,我有两个部分 my app and user我的应用程序 到 user header 重新呈现为什么? 这是我
我正在尝试在 React 应用程序中插入 google maps map 。我宁愿不使用非官方图书馆(我发现那些缺乏文档的图书馆),而且我已经成功地插入了 map 。 我的问题是每次父组件的状态改变时
我有一个父组件,它根据通过 props 接收到的数组来渲染子组件的集合。 import React from 'react'; import PropTypes from 'prop-types';
我只是使用 redux 和react-redux connect 函数以及状态和调度来连接应用程序。编译没有问题,但结果没有显示。如下所示。 我尝试查找,发现必须更换react版本。 $ sudo n
我习惯了export default React.memo(SomeComponent);所以 React 可以内存我的组件。 但是在我使用命名导出的文件中。如何使用 React.memo() ? e
我正在创建一个函数备忘录,返回一个函数,该函数在调用时将检查它是否已经计算出给定参数的结果,并在可能的情况下返回该值。 现在我的 key 仅包含作为我的 key 传入的第一个参数,以检查该函数是否已经
考虑以下简单组件: import React, { Fragment, memo } from 'react'; function Parent(props) { return (
我的父组件处理对服务器的请求并为其子组件提供来自响应的数据。在这种情况下,一个子组件(FilterSidebar:包含过滤器组件)应该只呈现一次,因为过滤器将从初始请求的数据创建。 这就是为什么我要使
是否可以将 React.memo 应用于带有 for 循环的组件数组? 假设我有以下三个组件: const Item1 = (props) => { const { index } = pro
我到处搜索有关此信息,似乎Access中的DAO参数限制为255个字符。 真的吗?仍然?即使在Office 2010中?看来很荒谬。我宁愿不切换到ADO,但在这一点上看来我必须这样做。 在仍然使用DA
每次我的选项卡组件父组件重新呈现时,我的子组件也会重新呈现。 我的标签组件父级如下 import { useState } from "react"; import "./styles.scss";
我正在重构我们的一些组件,所以我试图将 memoization 作为一些组件合并 5 月 使用相同的值重新渲染(例如,热链接图像 URL,除非它们相同)。 我有一个简单的组件: const CardH
我不想在某些路径上重新渲染我的组件,尝试使用 React.memo 并使用 withRouter HOC 检查当前路径。 React.memo 中的比较函数没有被调用。 function compar
我使用 React 前端制作了一个国际象棋游戏。最初,任何 Action 似乎都是瞬间实现的,但是在添加了额外的功能之后,比如改变标题的背景以反射(reflect)轮到谁了(白色或黑色背景取决于它的白
我正在尝试制作一个聊天应用程序,它将以如下形式将消息发布到备忘录中: USERNAME-> Message 但它像这样发布到我的备忘录中: USERNAME 这是我的代码: const cnMax
在 documentation for React.memo ,它说: This method only exists as a performance optimization. Do not re
有人知道当使用react-redux中的connect函数时如何用React.memo包装React组件吗? 例如,您将如何修改以下内容? let Button = (props: Props) =>
以下代码来自 Pathikrit's Dynamic Programming存储库。 我对它的美丽和独特性感到困惑。 def subsetSum(s: List[Int], t: Int) = {
我正在使用 Apollo GraphQL 中的 useMutation Hook ,并且我想使用 onCompleted 属性执行特定任务。基本上,我想在 useMutation 成功完成时执行 se
我是一名优秀的程序员,十分优秀!