Traté de buscar aquí para restablecer los valores de la matriz useState , pero no pude encontrar ninguna referencia a los valores de la matriz.
Intentando cambiar el valor desplegable del estado inicial a valores de estado permitido. Estoy usando el método de ganchos aquí para establecer los valores usando setStateValues . Si comento esa línea de código, muestra el menú desplegable. No pude entender por qué no puedo usar el método setStateValues para restablecer los valores de las variables de estado.
Recibo este siguiente error:
Demasiados renderizados. React limita el número de renderizados para evitar un bucle infinito
¿Hay algo mal aquí?
import React, { useState } from "react"; import ReactDOM from "react-dom"; const StateSelector = () => { const initialValue = [ { id: 0,value: " --- Select a State ---" }]; const allowedState = [ { id: 1, value: "Alabama" }, { id: 2, value: "Georgia" }, { id: 3, value: "Tennessee" } ]; const [stateOptions, setStateValues] = useState(initialValue); // initialValue.push(...allowedState); console.log(initialValue.length); setStateValues(allowedState); // Not sure why cannot I reset the state in here for an array. return (<div> <label>Select a State:</label> <select> {stateOptions.map((localState, index) => ( <option key={localState.id}>{localState.value}</option> ))} </select> </div> ); }; const rootElement = document.getElementById("root"); ReactDOM.render(<StateSelector />, rootElement);No debe establecer el estado (o hacer cualquier otra cosa con efectos secundarios) desde dentro de la función de renderizado. Cuando use ganchos, puede usar useEffect para esto.
La siguiente versión funciona:
import React, { useState, useEffect } from "react"; import ReactDOM from "react-dom"; const StateSelector = () => { const initialValue = [ { id: 0, value: " --- Select a State ---" }]; const allowedState = [ { id: 1, value: "Alabama" }, { id: 2, value: "Georgia" }, { id: 3, value: "Tennessee" } ]; const [stateOptions, setStateValues] = useState(initialValue); // initialValue.push(...allowedState); console.log(initialValue.length); // ****** BEGINNING OF CHANGE ****** useEffect(() => { // Should not ever set state during rendering, so do this in useEffect instead. setStateValues(allowedState); }, []); // ****** END OF CHANGE ****** return (<div> <label>Select a State:</label> <select> {stateOptions.map((localState, index) => ( <option key={localState.id}>{localState.value}</option> ))} </select> </div>); }; const rootElement = document.getElementById("root"); ReactDOM.render(<StateSelector />, rootElement);y aquí está en un entorno limitado de código .
Supongo que eventualmente desea cargar la lista de estados de alguna fuente dinámica (de lo contrario, podría usar allowedState directamente sin usar useState en absoluto). Si es así, esa llamada a la API para cargar la lista también podría ir dentro del bloque useEffect .
Trate de mantener su estado mínimo. No hay necesidad de almacenar
const initialValue = [ { id: 0,value: " --- Select a State ---" }];como estado Separar lo permanente de lo cambiante.
const ALL_STATE_VALS = [ { id: 0,value: " --- Select a State ---" } { id: 1, value: "Alabama" }, { id: 2, value: "Georgia" }, { id: 3, value: "Tennessee" } ];Luego puede almacenar solo la identificación como su estado:
const StateSelector = () =>{ const [selectedStateOption, setselectedStateOption] = useState(0); return ( <div> <label>Select a State:</label> <select> {ALL_STATE_VALS.map((option, index) => ( <option key={option.id} selected={index===selectedStateOption}>{option.value}</option> ))} </select> </div>); ) }Para ampliar la respuesta de Ryan:
Cada vez que se llama a setStateValues, React vuelve a renderizar su componente, lo que significa que el cuerpo de la función del componente StateSelector se vuelve a ejecutar.
Reaccionar documentos :
setState() siempre conducirá a una nueva representación a menos que shouldComponentUpdate() devuelva falso.
Esencialmente, estás configurando el estado con:
setStateValues(allowedState);provocando una nueva representación, que luego hace que la función se ejecute, y así sucesivamente. Por lo tanto, el problema del bucle.
Para ilustrar el punto, si establece un tiempo de espera como:
setTimeout( () => setStateValues(allowedState), 1000 )Lo que termina con el problema de 'demasiadas re-renderizaciones'.
En su caso, está lidiando con un efecto secundario, que se maneja con UseEffect en las funciones de su componente. Puedes leer más sobre esto aquí .