Как решал самую трудную техническую задачу

Ответ

Однажды столкнулся с проблемой оптимизации рендеринга большого списка (10k+ элементов) в React. Стандартный подход с map приводил к лагам. Решение:

  1. Виртуализация: использовал react-window для рендеринга только видимых элементов.
  2. Мемоизация: обернул элементы в React.memo, чтобы избежать лишних ререндеров.
  3. Оптимизация данных: разбил данные на чанки и добавил lazy loading.

Пример кода:

import { FixedSizeList as List } from 'react-window';

const Row = React.memo(({ index, style, data }) => (
  <div style={style}>{data[index]}</div>
));

function BigList({ items }) {
  return (
    <List
      height={600}
      itemCount={items.length}
      itemSize={50}
      width="100%"
      itemData={items}
    >
      {Row}
    </List>
  );
}

Ключевые моменты: анализ проблемы, выбор правильных инструментов, измерение производительности до/после.

Ответ 18+ 🔞

А, ну это классика, блядь! Ты тоже на эти грабли наступил, с этими десятью тысячами элементов? Ну, ясен пень, стандартный map тут тебе не союзник, а скорее враг, который тебе всю память в браузере сожрёт и интерфейс в слайд-шоу превратит. Полный пиздец, одним словом.

Так, слушай сюда, как я эту поебень раздолбал. Первое и главное — виртуализация. Это когда ты не рендеришь всё подряд, как последний распиздяй, а только то, что юзер в данный момент на экране видит. Остальное — в рот меня чих-пых, в небытии. Для этого есть библиотека react-window. Она тебе создаёт окно, и внутри него только видимые строки болтаются. Гениально и просто, как три копейки.

Второе — мемоизация. Ты ж не хочешь, чтобы каждый чих в родительском компоненте заставлял все десять тысяч дочерних перерисовываться? Вот и я не хотел. Поэтому каждый элемент списка нужно обернуть в React.memo. Пусть сидят тихо и не дергаются, если их пропсы не изменились. Экономия — овердохуища.

Ну и третье — данные. Если их реально дохуя и они с сервера прилетают, то тащить всё разом — это самоубийство. Нужно лениво чанками подгружать. Пока юзер скроллит вниз — ты ему подкидываешь новую порцию. Он доволен, браузер не падает, все в шоколаде.

Вот смотри, как это в коде выглядит, сука:

import { FixedSizeList as List } from 'react-window';

const Row = React.memo(({ index, style, data }) => (
  <div style={style}>{data[index]}</div>
));

function BigList({ items }) {
  return (
    <List
      height={600}
      itemCount={items.length}
      itemSize={50}
      width="100%"
      itemData={items}
    >
      {Row}
    </List>
  );
}

Видишь? Row обёрнут в memo, а List из react-window сам разберётся, что и когда показывать. Главное — правильно замерить производительность до и после, а то будешь как тот Герасим, с лучшими намерениями, а в итоге всё утопишь. Не будь мудаком, тестируй!