0

その中に会議の予約が入ったフォームがあります。これの一部は、かなり複雑な UI を持つカレンダー コンポーネントです。

<Calendar fullName={fullName} email={email} onEventScheduled={onEventScheduled} />

これはうまくいきます。

React ユーザーが知っているように、入力のいずれかが変更されると、react はフォームを再レンダリングします。fullNameカレンダーは一部の入力 ( 、emailおよび)にのみ依存し、他の入力には依存せず、描画が遅いため、カレンダーの再レンダリングを停止するためonEventScheduledに使用したいと思います。useMemo()

(@dmitryguzeev コメントごとに JSX を使用するように更新)

  const MemoizedCalendar = useMemo(() => {
    return <Calendar fullName={fullName} email={email} onEventScheduled={onEventScheduled} />;
  }, [email, fullName, onEventScheduled]);

そしてその後

<MemoizedCalendar fullName={fullName} email={email} onEventScheduled={onEventScheduled} />

ただし、MemoizedCalendar にスワップすると、次のエラーが発生します。

Error: Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: object.

Check the render method of `Formik`.

(たまたまFormikを使用していますが、コンポーネントは上記で正常に動作しますが、失敗Calendarするだけです)MemoizedCalendar

編集: UseMemo() に関するこの記事を読んだuseCallback()後も試しました

コンポーネントが prop として関数を受け取る場合、useCallback フックを使用する必要があることは言うまでもありません。これにより、必要な場合にのみ関数が再度宣言されるようになります。そうしないと、関数プロップには常に新しい参照があるため、プロップはレンダリングごとに異なります。

const MemoizedCalendar = useCallback(() => {
    return Calendar(email, fullName, onEventScheduled);
  }, [email, fullName, onEventScheduled]);

emailこれにより、エラーは修正されますが、 、fullName、および以外の項目が変更されると、不必要に再レンダリングonEventScheduledされます。

このフックコンポーネントをメモ化するにはどうすればよいですか?

4

1 に答える 1