Javascript React use状态数组不更新
我正在尝试调用API获取天气数据,我需要将每个返回的数据添加到数组状态。但它不起作用,只显示最后添加的数据。有人能解释一下为什么会这样,并给我一个解决方案吗Javascript React use状态数组不更新,javascript,reactjs,axios,Javascript,Reactjs,Axios,我正在尝试调用API获取天气数据,我需要将每个返回的数据添加到数组状态。但它不起作用,只显示最后添加的数据。有人能解释一下为什么会这样,并给我一个解决方案吗 import React, {useEffect, useState} from 'react'; import './App.css'; const data = require('../src/data/Step1'); //Importing json file const axios = require("axios&
import React, {useEffect, useState} from 'react';
import './App.css';
const data = require('../src/data/Step1'); //Importing json file
const axios = require("axios");
function App() {
//React Hook to save weather data
const [weatherData, setWeatherData] = useState([]);
//UseEffect to call getData function
useEffect(() => {
//call getData for each sending city code one by one
data.List.map(city => getData(city.CityCode));
}, []);
//getData function
async function getData(cityCode) {
//Axios get request to http get request
const response = await axios.get('http://api.openweathermap.org/data/2.5/group?id=' + cityCode + '&units=metric&appid=24e343673cb58392072a12e4705b1260');
//adding each weather object to weather data Array
setWeatherData([...weatherData,response.data.list[0]]);
}
if (weatherData.length > 1) {
return (
<div>
{
<div className="container mt-5">
{weatherData.map(x => (
<div className="row mt-2 ">
Id : {x.data.id} {" | "}
Name :{x.data.name} {" | "}
Description : {x.data.weather[0].description} {" | "}
Temperature : {x.data.main.temp}
</div>
))}
</div>
}
</div>
);
} else {
return (
<div>
<h1>Loading</h1>
</div>
)
}
}
export default App;
import React,{useffect,useState}来自“React”;
导入“/App.css”;
const data=require('../src/data/Step1')//导入json文件
常量axios=要求(“axios”);
函数App(){
//React钩子保存天气数据
const[weatherData,setWeatherData]=useState([]);
//使用effect调用getData函数
useffect(()=>{
//逐个调用每个发送城市代码的getData
data.List.map(city=>getData(city.CityCode));
}, []);
//getData函数
异步函数getData(cityCode){
//Axios get请求到http get请求
const response=等待axios.get('http://api.openweathermap.org/data/2.5/group?id=“+cityCode+”&units=metric&appid=24e343673cb58392072a12e4705b1260”);
//将每个天气对象添加到天气数据数组
setWeatherData([…weatherData,response.data.list[0]]);
}
如果(weatherData.length>1){
返回(
{
{weatherData.map(x=>(
Id:{x.data.Id}{“|”}
名称:{x.data.Name}{“|”}
Description:{x.data.weather[0]。Description}{“|”}
温度:{x.data.main.temp}
))}
}
);
}否则{
返回(
加载
)
}
}
导出默认应用程序;
实际上,回调weatherData是一个。也许以下方法可以奏效:
//using useCallback so the dependency of getData to the
// effect won't cause the effect to run other than when
// the component mounts
const getData = React.useCallback(async function getData(
cityCode
) {
const response = await axios.get(
'http://api.openweathermap.org/data/2.5/group?id=' +
cityCode +
'&units=metric&appid=24e343673cb58392072a12e4705b1260'
);
setWeatherData((weatherData) => [
//using callback so weatherData is not a dependency
...weatherData,
response.data.list[0],
]);
},
[]);
useEffect(() => {
//if you don't use the result of a map then use forEach instead
data.List.forEach((city) => getData(city.CityCode));
}, [getData]);
您可以将回调传递给状态设置器
setWeatherData
,该设置器接收当前状态并返回新状态。设置状态不会同步发生,因此您不能保证下次调用时状态会更新。相反,请尝试以下方法
async function getData(cityCode) {
const response = await axios.get('http://api.openweathermap.org/data/2.5/group?id=' + cityCode + '&units=metric&appid=24e343673cb58392072a12e4705b1260');
//adding each weather object to weather data Array
setWeatherData(function (currentWeatherData) {
return [...currentWeatherData, response.data.list[0]];
});
}
下面是一个repl示例您可以正确地看到setState是异步的,但使用挂钩时回调的效果是weatherData。这就是为什么linter会指出这一点,但添加它会使效果运行太多次,因此解决方案将向setWeatherData传递回调。所以你的答案是正确的,但没有正确解释为什么它不起作用。