Junior
Como alterar corretamente o estado dos componentes no React?
sobes.tech IA
Resposta da IA
A alteração de estado no React ocorre através do método setState para componentes de classe ou usando o hook useState para componentes funcionais.
Componentes de classe:
// Importamos React
import React, { Component } from 'react';
// Criamos um componente de classe
class MyComponent extends Component {
// Inicializamos o estado
constructor(props) {
super(props);
this.state = {
count: 0
};
}
// Método para alterar o estado
incrementCount = () => {
// Usamos setState
this.setState({ count: this.state.count + 1 });
};
render() {
return (
<div>
<p>Contador: {this.state.count}</p>
<button onClick={this.incrementCount}>Incrementar</button>
</div>
);
}
}
// Exportamos o componente
export default MyComponent;
setStateé assíncrono.setStatecombina o novo estado com o atual (shallow merge).setStatepode aceitar uma função que retorna um novo estado baseado no anterior:
// Método para alterar o estado usando uma função
incrementCountFunction = () => {
this.setState((prevState) => ({
count: prevState.count + 1
}));
};
Componentes funcionais (usando useState):
// Importamos React e useState
import React, { useState } from 'react';
// Criamos um componente funcional
function MyFunctionComponent() {
// Inicializamos o estado com useState
const [count, setCount] = useState(0); // [estado atual, função para atualizar]
// Função para alterar o estado
const incrementCount = () => {
// Usamos a função para atualizar o estado
setCount(count + 1);
};
return (
<div>
<p>Contador: {count}</p>
<button onClick={incrementCount}>Incrementar</button>
</div>
);
}
// Exportamos o componente
export default MyFunctionComponent;
useStateretorna um array de dois elementos: o estado atual e a função para atualizá-lo.- A função de atualização de estado, retornada por
useState, substitui o estado atual, não o combina. - Pode-se passar uma função para a função de atualização se o novo estado depender do anterior:
// Função para alterar o estado usando uma função
const incrementCountFunction = () => {
setCount(prevCount => prevCount + 1);
};
Pontos importantes ao alterar o estado:
- Não modifique o estado diretamente: Nunca atribua um novo valor à propriedade
statediretamente (por exemplo,this.state.count = 5oucount = 5). React não detectará essa mudança e o componente não será rerenderizado. - Alteração de objetos e arrays: Ao modificar objetos ou arrays no estado, crie sempre novas cópias. React compara referências de objetos/arrays, e se a referência não mudar, React assume que os dados não mudaram e não rerenderiza.
// Alteração de objeto em componente de classe
this.setState(prevState => ({
user: {
...prevState.user, // Copiando as propriedades antigas
name: 'Novo nome' // Atualizando a propriedade necessária
}
}));
// Alteração de array em componente funcional
setItems(prevItems => [...prevItems, 'Novo elemento']); // Adiciona um novo elemento
- Assincronidade de
setState: Se precisar executar uma ação após o estado ser atualizado e o componente rerenderizar, use o segundo argumento desetState(função de callback) ou o hookuseEffectem componentes funcionais.
// Callback em setState
this.setState({ count: this.state.count + 1 }, () => {
console.log('Estado atualizado!');
});
// useEffect para reagir à mudança de estado
useEffect(() => {
console.log('O estado count mudou:', count);
}, [count]); // Dependência: o hook será acionado ao mudar count
Comparação de métodos:
| Característica | Componente de classe (setState) |
Componente funcional (useState) |
|---|---|---|
| Sintaxe | Método this.setState(newState[, callback]) |
Hook const [state, setState] = useState(initialState) |
| União/Substituição | Combina o novo estado com o atual (shallow merge) | Substitui o estado atual pelo novo |
| Assincronia | Assíncrono | A função de atualização é assíncrona quando chamada de manipuladores de eventos, mas síncrona na fase de render do React |
| Dependência do estado anterior | Passar uma função para setState: this.setState(prevState => ({...})) |
Passar uma função para a função de atualização: setState(prev => ({...})) |