gpt4 book ai didi

javascript - 在没有 React.memo 的情况下使用 useCallback 有什么好处吗?

转载 作者:行者123 更新时间:2023-12-04 13:39:27 24 4
gpt4 key购买 nike

从我从 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/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com