I am a bit new to react and hooks, There are many similar problems but I just need to understand it for my case. I am getting the data from the backend as an array of objects I want to display each element, but the useSate function doesn't keep the old data of the loop so only the last element is displayed, Do I need to add another useEffect ? or the code is not correct ?
const [department, setdepartment] = useState([
{ departmentName: "Departm 1", departmentID: 1 },
{ departmentName: "Departm 2", departmentID: 1 },
{ departmentName: "Departm 3", departmentID: 1 },
useEffect(() => {
axios
.get("http://localhost:8080/api/department")
.then((response) => {
console.log(response.data);
for (let i = 0; i < response.data.data.length; i ) {
let dep = {
departmentName: response.data.data[i].name,
departmentID: response.data.data[i]._id,
};
setdepartment([...department, dep]);
}
})
.catch((error) => console.log(error));
}, []);
CodePudding user response:
This is a case where map
would be a better choice than a for loop. If you map over the result data, you can create the shape you want, and then set it all in state at once. By calling setDepartment
on every iteration, you're causing the component to re-render with every iteration. If you transform with .map
before calling setDepartment
, you'll only re-render once.
axios
.get("http://localhost:8080/api/department")
.then((response) => {
console.log(response.data);
const departmentData = response.data.data.map(({name, _id}) => {
return {
departmentName: name,
departmentID: _id,
};
});
setdepartment((prev) => [...prev, ...departmentData]);
})
prev
is the existing department
data , it's a little simpler if you can overwrite the initial data:
setdepartment(departmentData);