Пропсы и состояние компонента — неизменяемые снимки. Никогда не мутируйте их напрямую. Вместо этого передавайте новые пропсы вниз и используйте функцию-сеттер из useState.
// ✅ Create new arrayfunctionComponent(){const[items,setItems]=useState([1,2,3]);constaddItem=()=>{setItems([...items,4]);// New array};}// ✅ Create new objectfunctionComponent(){const[user,setUser]=useState({name:'Alice'});constupdateName=()=>{setUser({...user,name:'Bob'});// New object};}
Мутация массива методами вроде push() не вызывает повторный рендер:
1 2 3 4 5 6 7 8 9101112131415
// ❌ Wrong: Mutating the arrayfunctionTodoList(){const[todos,setTodos]=useState([]);constaddTodo=(id,text)=>{todos.push({id,text});setTodos(todos);// Same array reference!};return(<ul>{todos.map(todo=><likey={todo.id}>{todo.text}</li>)}</ul>);}
Создайте новый массив:
1 2 3 4 5 6 7 8 9101112131415
// ✅ Better: Create a new arrayfunctionTodoList(){const[todos,setTodos]=useState([]);constaddTodo=(id,text)=>{setTodos([...todos,{id,text}]);// Or: setTodos(todos => [...todos, {id: Date.now(), text}])};return(<ul>{todos.map(todo=><likey={todo.id}>{todo.text}</li>)}</ul>);}
Мутация вложенных свойств не вызывает повторный рендер:
1 2 3 4 5 6 7 8 9101112131415
// ❌ Wrong: Mutating nested objectfunctionUserProfile(){const[user,setUser]=useState({name:'Alice',settings:{theme:'light',notifications:true}});consttoggleTheme=()=>{user.settings.theme='dark';// Mutation!setUser(user);// Same object reference};}
Скопируйте через spread каждый уровень, который нужно обновить:
1 2 3 4 5 6 7 8 91011121314151617181920
// ✅ Better: Create new objects at each levelfunctionUserProfile(){const[user,setUser]=useState({name:'Alice',settings:{theme:'light',notifications:true}});consttoggleTheme=()=>{setUser({...user,settings:{...user.settings,theme:'dark'}});};}