Български

Научете как автоматичното групиране на React оптимизира множество актуализации на състоянието, подобрявайки производителността на приложението и предотвратявайки ненужни повторни рендерирания. Разгледайте примери и най-добри практики.

Автоматично групиране на React: Оптимизиране на актуализациите на състоянието за производителност

Производителността на React е от решаващо значение за създаването на плавни и отзивчиви потребителски интерфейси. Една от ключовите функции, въведени за подобряване на производителността, е автоматичното групиране. Тази техника за оптимизация автоматично групира множество актуализации на състоянието в едно повторно рендериране, което води до значителни подобрения в производителността. Това е особено важно в сложни приложения с чести промени в състоянието.

Какво е автоматично групиране на React?

Групирането, в контекста на React, е процесът на групиране на множество актуализации на състоянието в една актуализация. Преди React 18, групирането се прилагаше само към актуализации, които се случваха вътре в обработчиците на събития на React. Актуализации извън обработчиците на събития, като тези в setTimeout, promises или native event handlers, не бяха групирани. Това можеше да доведе до ненужни повторни рендерирания и затруднения в производителността.

React 18 въведе автоматично групиране, което разширява тази оптимизация към всички актуализации на състоянието, независимо от това къде се случват. Това означава, че независимо дали вашите актуализации на състоянието се случват вътре в обработчик на събития на React, setTimeout callback или promise resolution, React автоматично ще ги групира заедно в едно повторно рендериране.

Защо е важно автоматичното групиране?

Автоматичното групиране предоставя няколко ключови предимства:

Как работи автоматичното групиране

React постига автоматично групиране, като забавя изпълнението на актуализациите на състоянието до края на текущия контекст на изпълнение. Това позволява на React да събере всички актуализации на състоянието, които са се случили по време на този контекст, и да ги групира заедно в една актуализация.

Разгледайте този опростен пример:

function ExampleComponent() {
  const [count1, setCount1] = useState(0);
  const [count2, setCount2] = useState(0);

  function handleClick() {
    setTimeout(() => {
      setCount1(count1 + 1);
      setCount2(count2 + 1);
    }, 0);
  }

  return (
    <div>
      <p>Count 1: {count1}</p>
      <p>Count 2: {count2}</p>
      <button onClick={handleClick}>Increment</button>
    </div>
  );
}

Преди React 18, щракването върху бутона ще задейства две повторни рендерирания: едно за setCount1 и друго за setCount2. С автоматичното групиране в React 18, и двете актуализации на състоянието се групират заедно, което води само до едно повторно рендериране.

Примери за автоматично групиране в действие

1. Асинхронни актуализации

Асинхронните операции, като например извличане на данни от API, често включват актуализиране на състоянието след завършване на операцията. Автоматичното групиране гарантира, че тези актуализации на състоянието се групират заедно, дори ако се случват в рамките на асинхронния callback.

function DataFetchingComponent() {
  const [data, setData] = useState(null);
  const [loading, setLoading] = useState(true);

  useEffect(() => {
    async function fetchData() {
      try {
        const response = await fetch('https://api.example.com/data');
        const jsonData = await response.json();
        setData(jsonData);
        setLoading(false);
      } catch (error) {
        console.error('Error fetching data:', error);
        setLoading(false);
      }
    }

    fetchData();
  }, []);

  if (loading) {
    return <p>Loading...</p>;
  }

  return <div>Data: {JSON.stringify(data)}</div>;
}

В този пример, setData и setLoading са извикани в рамките на асинхронната функция fetchData. React ще групира тези актуализации заедно, което води до едно повторно рендериране, след като данните бъдат извлечени и състоянието на зареждане бъде актуализирано.

2. Promises

Подобно на асинхронните актуализации, promises често включват актуализиране на състоянието, когато promise-ът се разреши или отхвърли. Автоматичното групиране гарантира, че тези актуализации на състоянието също се групират заедно.

function PromiseComponent() {
  const [result, setResult] = useState(null);
  const [error, setError] = useState(null);

  useEffect(() => {
    const myPromise = new Promise((resolve, reject) => {
      setTimeout(() => {
        const success = Math.random() > 0.5;
        if (success) {
          resolve('Promise resolved!');
        } else {
          reject('Promise rejected!');
        }
      }, 1000);
    });

    myPromise
      .then((value) => {
        setResult(value);
        setError(null);
      })
      .catch((err) => {
        setError(err);
        setResult(null);
      });
  }, []);

  if (error) {
    return <p>Error: {error}</p>;
  }

  if (result) {
    return <p>Result: {result}</p>;
  }

  return <p>Loading...</p>;
}

В този случай, или setResult и setError(null) се извикват при успех, или setError и setResult(null) се извикват при неуспех. Независимо от това, автоматичното групиране ще ги комбинира в едно повторно рендериране.

3. Native Event Handlers

Понякога може да се наложи да използвате native event handlers (напр. addEventListener) вместо synthetic event handlers на React. Автоматичното групиране също работи в тези случаи.

function NativeEventHandlerComponent() {
  const [scrollPosition, setScrollPosition] = useState(0);

  useEffect(() => {
    function handleScroll() {
      setScrollPosition(window.scrollY);
    }

    window.addEventListener('scroll', handleScroll);

    return () => {
      window.removeEventListener('scroll', handleScroll);
    };
  }, []);

  return <p>Scroll Position: {scrollPosition}</p>;
}

Въпреки че setScrollPosition се извиква в рамките на native event handler, React все пак ще групира актуализациите заедно, предотвратявайки прекомерни повторни рендерирания, докато потребителят превърта.

Отказване от автоматично групиране

В редки случаи може да искате да се откажете от автоматичното групиране. Например, може да искате да принудите синхронна актуализация, за да сте сигурни, че потребителският интерфейс се актуализира незабавно. React предоставя flushSync API за тази цел.

Забележка: Използването на flushSync трябва да се прави пестеливо, тъй като може да повлияе отрицателно на производителността. Обикновено е най-добре да разчитате на автоматичното групиране, когато е възможно.

import { flushSync } from 'react-dom';

function ExampleComponent() {
  const [count, setCount] = useState(0);

  function handleClick() {
    flushSync(() => {
      setCount(count + 1);
    });
  }

  return (<button onClick={handleClick}>Increment</button>);
}

В този пример, flushSync принуждава React незабавно да актуализира състоянието и да рендерира повторно компонента, заобикаляйки автоматичното групиране.

Най-добри практики за оптимизиране на актуализациите на състоянието

Въпреки че автоматичното групиране осигурява значителни подобрения в производителността, все още е важно да следвате най-добрите практики за оптимизиране на актуализациите на състоянието:

Автоматично групиране и глобални съображения

Автоматичното групиране, като основна оптимизация на производителността на React, е от полза за приложенията в световен мащаб, независимо от местоположението на потребителя, скоростта на мрежата или устройството. Въпреки това, неговото въздействие може да бъде по-забележимо в сценарии с по-бавни интернет връзки или по-слаби устройства. За международна аудитория обмислете следните точки:

Заключение

Автоматичното групиране на React е мощна техника за оптимизация, която може значително да подобри производителността на вашите React приложения. Чрез автоматично групиране на множество актуализации на състоянието в едно повторно рендериране, то намалява разходите за рендериране, предотвратява непоследователни състояния и води до по-плавно и по-отзивчиво потребителско изживяване. Като разберете как работи автоматичното групиране и следвате най-добрите практики за оптимизиране на актуализациите на състоянието, можете да изградите React приложения с висока производителност, които предоставят страхотно потребителско изживяване на потребителите по целия свят. Използването на инструменти като React DevTools помага допълнително да се прецизират и оптимизират профилите на производителност на вашето приложение в различни глобални настройки.