Комментарии (1)
Ответ сгенерирован нейросетью и может содержать ошибки
Hooks жизненного цикла в React
Что такое жизненный цикл?
Жизненный цикл компонента — это периоды его существования: монтирование (mount), обновление (update) и размонтирование (unmount). В функциональных компонентах React мы управляем жизненным циклом через Hooks.
useEffect — основной Hook для побочных эффектов
useEffect — это комбинация методов жизненного цикла componentDidMount, componentDidUpdate и componentWillUnmount.
useEffect(() => {
console.log('Компонент смонтирован или обновлён');
return () => {
console.log('Компонент размонтирован');
};
}, []);
Три варианта useEffect
1. Без массива зависимостей — запускается после КАЖДОГО рендера
useEffect(() => {
console.log('После каждого рендера');
});
2. С пустым массивом — запускается только при монтировании
useEffect(() => {
console.log('Компонент смонтирован');
return () => {
console.log('Компонент размонтирован');
};
}, []);
3. С зависимостями — запускается при изменении зависимостей
const [count, setCount] = useState(0);
useEffect(() => {
console.log('Count изменился на:', count);
}, [count]);
Практические примеры
Пример 1: Загрузка данных
function UserProfile({ userId }) {
const [user, setUser] = useState(null);
const [loading, setLoading] = useState(true);
useEffect(() => {
setLoading(true);
fetch(`/api/users/${userId}`)
.then(res => res.json())
.then(data => {
setUser(data);
setLoading(false);
});
}, [userId]);
return loading ? <p>Загрузка...</p> : <p>{user.name}</p>;
}
Пример 2: Подписка на событие
function WindowSize() {
const [size, setSize] = useState(window.innerWidth);
useEffect(() => {
const handleResize = () => setSize(window.innerWidth);
window.addEventListener('resize', handleResize);
return () => {
window.removeEventListener('resize', handleResize);
};
}, []);
return <p>Ширина окна: {size}px</p>;
}
Пример 3: Таймер/Интервал
function Timer() {
const [seconds, setSeconds] = useState(0);
useEffect(() => {
const interval = setInterval(() => {
setSeconds(s => s + 1);
}, 1000);
return () => clearInterval(interval);
}, []);
return <p>Время: {seconds}s</p>;
}
useLayoutEffect — синхронное выполнение
Похож на useEffect, но выполняется синхронно после изменения DOM и перед браузерной перерисовкой.
useLayoutEffect(() => {
const width = document.getElementById('box').offsetWidth;
console.log(width);
}, []);
Когда использовать useLayoutEffect:
- Измерение размеров элементов
- Управление фокусом
- Синхронизация с внешними библиотеками
- Определение позиции элемента
Сравнение жизненных циклов
- Монтирование: useEffect(fn, [])
- Обновление: useEffect(fn, [deps])
- Размонтирование: return () => {} в useEffect
- Синхронная работа: useLayoutEffect
useRef для работы между рендерами
function TextInput() {
const inputRef = useRef(null);
useEffect(() => {
inputRef.current.focus();
}, []);
return <input ref={inputRef} />;
}
Важные правила Hooks
- Вызывай только на верхнем уровне — не в условиях, циклах или функциях
- Только в компонентах — в функциональных компонентах или кастомных Hooks
- Порядок важен — не меняй количество и порядок Hooks
- Зависимости — всегда указывай правильный массив зависимостей
Кастомные Hooks для переиспользования логики
function useWindowSize() {
const [size, setSize] = useState(window.innerWidth);
useEffect(() => {
const handleResize = () => setSize(window.innerWidth);
window.addEventListener('resize', handleResize);
return () => window.removeEventListener('resize', handleResize);
}, []);
return size;
}
function MyComponent() {
const windowSize = useWindowSize();
return <p>Размер: {windowSize}px</p>;
}
Правильное использование Hooks жизненного цикла — ключ к чистому и эффективному коду в React.