简体   繁体   English

在没有 React.memo 的组件中使用 useCallback 有什么意义?

[英]What is the point to use useCallback in a component without React.memo?

Consider example:考虑示例:

const Child = () => {
  console.log("I did re-render!");
  return null;
};

const App = () => {
  const [_, setValue] = useState();
  const fn = useCallback(() => {
    // do something
  }, []);

  return (
    <div>
      <button onClick={() => setValue(Math.random)}>click</button>
      <Child fn={fn} />
    </div>
  );
};

With every state change in App (click the button), the Child component re-renders, even if the passed prop fn is wrapped with useCallback .随着App中的每个 state 更改(单击按钮), Child组件会重新渲染,即使传递的道具fnuseCallback包装。 However, if I wrap Child with React.memo , it starts to work correctly - it does not re-render when parent re-renders.但是,如果我用React.memo包装Child ,它就会开始正常工作 - 当父级重新渲染时它不会重新渲染。

My question: What's the point of using useCallbacks without React.memo ??我的问题:在没有React.memo的情况下使用useCallbacks有什么意义? Should I always use React.memo if I dont want the component to always re-render if its parent re-renders?如果我不希望组件在其父组件重新渲染时始终重新渲染,我是否应该始终使用React.memo

Should useCallbacks always be used with React.memo ? useCallbacks是否应该始终与React.memo一起使用? Because it seems like they are senseless and useless without React.memo .因为如果没有React.memo ,它们似乎毫无意义和无用。

Playground: https://codesandbox.io/s/peaceful-khorana-nrojpb?file=/src/App.js操场: https://codesandbox.io/s/peaceful-khorana-nrojpb?file=/src/App.js

My question: What's the point of using useCallbacks without React.memo??我的问题:在没有 React.memo 的情况下使用 useCallbacks 有什么意义?

There is none unless you otherwise tell React to compare based on refernece down the line.除非你告诉 React 根据参考进行比较,否则没有。

Should I always use React.memo if I dont want the component to always re-render if its parent re-renders?如果我不希望组件在其父组件重新渲染时始终重新渲染,我是否应该始终使用 React.memo?

Yes, or something equivalent.是的,或者类似的东西。

Should useCallbacks always be used with React.memo? useCallbacks 是否应该始终与 React.memo 一起使用? Because it seems like they are senseless and useless without React.memo.因为如果没有 React.memo,它们似乎毫无意义和无用。

Yes, unless you do something equivalent.是的,除非你做同样的事情。


Just to elaborate - other than React.memo you can always wrap a sub-render with useMemo :只是为了详细说明 - 除了React.memo ,您始终可以使用useMemo包装子渲染:


const App = () => {
  const [_, setValue] = useState();
  const fn = useCallback(() => {
    // do something
  }, []);

  const child = useMemo(() => <Child fn={fn} />, [fn]);
  return (
    <div>
      <button onClick={() => setValue(Math.random)}>click</button>
      {child}
    </div>
  );
};

Or "roll your own" with useRef+useEffect or use class components and override shouldComponentUpdate or inherit from React.PureComponent .或者使用 useRef+useEffect “自己动手”,或者使用 class 组件并覆盖shouldComponentUpdate或从React.PureComponent继承。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM