Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion lessons/lesson31/examples/useEffectPage/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -45,11 +45,12 @@ function UseEffectPage3({ userId = 2 }) {
// Эффект, зависящий от userId
useEffect(() => {
if (!userId) return;
setIsLoading(true);

console.log("Сработаю при монтировании и изменении userId");

fetch(`https://jsonplaceholder.typicode.com/users/${userId}`)
.then((response) => response.json)
.then((response) => response.json())
.then((json) => setUser(json))
.catch((error) => console.error("Ошибка загрузки:", error))
.finally(() => setIsLoading(false));
Expand Down
5 changes: 5 additions & 0 deletions lessons/lesson31/examples/useMemoPage/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,16 @@ const todos = [

function UseMemoPage() {
const [filter, setFilter] = useState("all");
const [counter, setCounter] = useState(0);

return (
<div style={{ padding: "20px" }}>
<h1>useMemo</h1>

<button onClick={() => setCounter((count) => count + 1)}>
Счётчик: {counter} (не влияет на TodoList!)
</button>

{/* Кнопки фильтров */}
<div style={{ marginBottom: "20px" }}>
<h3>Выберите фильтр:</h3>
Expand Down
37 changes: 28 additions & 9 deletions lessons/lesson31/lesson.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,24 @@ description: "Hooks в React: useState, useEffect, useCallback, useMemo"

<!-- v -->

Жизненный цикл компонента в React

```
1. МОНТИРОВАНИЕ - Mounting
├── Конструктор / useState
├── Рендер (первый)
└── useEffect с пустым массивом зависимостей

2. ОБНОВЛЕНИЕ - Updating (может повторяться много раз)
├── Рендер (из-за изменения пропсов/состояния)
└── useEffect (в зависимости от deps)

3. РАЗМОНТИРОВАНИЕ - Unmounting
└── Функция очистки useEffect
```

<!-- v -->

<img src="./images/react-lifecycle.jpg" title="react lifecicles" />

<!-- v -->
Expand Down Expand Up @@ -66,25 +84,25 @@ const [state, setState] = useState(initialState);
```jsx
// ❌ ПЛОХО - не работает
function Counter() {
const [age, setAge] = useState(0);
const [count, setCount] = useState(0);

const increment = () => {
setAge(age + 1); // setCount(0 + 1) → setCount(1)
setAge(age + 1); // setCount(0 + 1) → setCount(1)
// Результат: age увеличится только на 1, а не на 2!
setCount(count + 1); // setCount(0 + 1) → setCount(1)
setCount(count + 1); // setCount(0 + 1) → setCount(1)
// Результат: count увеличится только на 1, а не на 2!
};

return <button onClick={increment}>+2</button>;
}

// ✅ ХОРОШО - работает правильно
function Counter() {
const [age, setAge] = useState(0);
const [count, setCount] = useState(0);

const increment = () => {
setAge((prev) => prev + 1); // prev = 0 → 1
setAge((prev) => prev + 1); // prev = 1 → 2
// Результат: age = 2
setCount((prev) => prev + 1); // prev = 0 → 1
setCount((prev) => prev + 1); // prev = 1 → 2
// Результат: count = 2
};

return <button onClick={increment}>+2</button>;
Expand Down Expand Up @@ -290,9 +308,10 @@ export default function UseEffectPage({ userId = 2 }) {

useEffect(() => {
if (!userId) return;
setIsLoading(true);

fetch(`https://jsonplaceholder.typicode.com/users/${userId}`)
.then((response) => response.json)
.then((response) => response.json())
.then((json) => setUser(json))
.catch((error) => console.error("Ошибка загрузки:", error))
.finally(() => setIsLoading(false));
Expand Down