webroad.online
  1. 1Веб
  2. 2HTML
  3. 3CSS
  4. 4JavaScript
  5. 5TypeScript
  6. 6Git
  7. 7Инструменты
  8. 8React
  9. 9Стейт-менеджмент
  10. 10Next.js
  11. 11Формы
  12. 12Данные и бэкенд
  13. 13SEO
  14. 14Tailwind CSS
  15. 15Анимации
  16. 16Тестирование
  17. 17Архитектура
React · Урок 6 из 7

Производительность в React

Почему компонент перерисовывается, memo, useMemo, useCallback, useTransition, виртуализация.

Обновлено

Что значит производительность в React

React-приложение обычно тормозит по одной из двух причин: оно слишком часто перерисовывается (пересчитываются компоненты, которые не изменились) или делает слишком много работы за один рендер (список из 5000 строк, тяжёлое вычисление). Перед любой оптимизацией — измеряйте: React DevTools → Profiler.

Когда компонент перерисовывается

  1. Изменилось его состояние.
  2. Перерисовался родитель (по умолчанию перерисовываются все дети — даже если props одинаковые).
  3. Изменилось значение Context, который он читает.

Перерисовка не означает изменения DOM — React сравнивает результат и трогает DOM только там, где есть разница. Обычно перерисовки дешёвые; проблемой они становятся у больших или очень частых компонентов.

Инструменты — что делает каждый

Инструмент Что делает Когда
перенос состояния ниже перерисовывается только маленький компонент первый вариант, бесплатно
children как prop переданное содержимое не перерисовывается вместе с родителем обёртки с состоянием (модалка, аккордеон)
memo(Component) пропускает перерисовку, если props равны (Object.is) дорогой компонент, часто перерисовываемый с теми же props
useMemo(() => calc, deps) сохраняет результат вычисления тяжёлое вычисление или объект, передаваемый в memo
useCallback(fn, deps) сохраняет ту же функцию между рендерами функция, передаваемая в memo или используемая в deps
useTransition / useDeferredValue помечает обновление как несрочное фильтрация большого списка при вводе — поле остаётся плавным
виртуализация рендерит только видимые строки списки из тысяч элементов (TanStack Virtual)

React Compiler

React Compiler анализирует код при сборке и автоматически добавляет мемоизацию (аналог memo / useMemo / useCallback) там, где нужно. С ним вы пишете простой код, а большая часть ручной мемоизации становится лишней. Next.js поддерживает его через опцию reactCompiler в next.config.ts.

Условие: код соблюдает правила React — чистые компоненты, без мутации props и состояния.

Ловушка ссылок

const Row = memo(function Row({ item, onSelect }) { ... })

function List({ items }) {
  return items.map(item => (
    <Row key={item.id} item={item} onSelect={() => select(item.id)} />   // НОВАЯ функция на каждом рендере
  ))
}

memo сравнивает props по ссылке; функция или объект, созданные прямо в JSX, всегда «новые» → memo не помогает. Отсюда useCallback / useMemo — или React Compiler.

Порядок оптимизации

  1. Измерьте (Profiler): какой компонент, сколько длится, почему перерисовывается.
  2. Перенесите состояние ближе к месту использования; разделите компоненты.
  3. Server Components для всего неинтерактивного — нулевая стоимость на клиенте.
  4. Виртуализация для длинных списков; useTransition для тяжёлых обновлений.
  5. Точечные memo / useMemo / useCallback — или включите React Compiler.

Коротко

  • Перерисовка = своё состояние, перерисованный родитель или изменённый Context; измеряйте в Profiler.
  • Сначала структура (состояние ниже, children), потом memo + useMemo / useCallback.
  • useTransition для тяжёлых обновлений, виртуализация для больших списков, React Compiler для автоматической мемоизации.

Официальные источники

Упражнения

Была ли страница полезной?

Один клик — без регистрации.