React无限滚动练习:首次渲染重复加载图片问题求助
问题原因
React 18+的开发环境中,StrictMode会自动重复执行一次副作用(包括空依赖的useEffect),目的是检测潜在的副作用问题。你的代码里useEffect空依赖本应只执行一次,但在StrictMode下会被调用两次,导致getPic发起两次API请求,所以首次加载出现两张图片。
修复方案
方案1:临时关闭开发环境的StrictMode
找到项目入口文件(通常是index.js或main.jsx),去掉包裹App的<StrictMode>标签:
// 原代码 ReactDOM.createRoot(document.getElementById('root')).render( <StrictMode> <App /> </StrictMode> ); // 修改后 ReactDOM.createRoot(document.getElementById('root')).render( <App /> );
注意:生产环境下StrictMode不会触发重复执行,上线后不会有这个问题,该方案适合开发调试时使用。
方案2:添加加载状态防止重复请求
如果不想关闭StrictMode,可以增加一个加载状态,确保同一时间只有一个API请求在进行:
function App() { const [data, setData] = useState([]); const [isLoading, setIsLoading] = useState(false); // 新增加载状态 useEffect(() => { getPic(); }, []); const getPic = useCallback(async () => { if (isLoading) return; // 如果正在加载,直接返回 setIsLoading(true); try { const pic = await axios({ url: "https://api.thecatapi.com/v1/images/search", }); const picUrl = pic.data[0]; if (picUrl) { setData((prevData) => [...prevData, picUrl]); } } catch (error) { console.log(`error = ${error}`); } finally { setIsLoading(false); // 请求完成后重置加载状态 } }, [isLoading]); // 依赖项添加isLoading return ( <div className="App"> <p>test</p> <div> {data.map((d) => ( <div key={d.id}> <S.CatImg src={d.url} alt="" /> </div> ))} </div> </div> ); } export default App;
这个方案在开发和生产环境都能生效,同时也能避免后续无限滚动时可能出现的重复请求问题。
内容的提问来源于stack exchange,提问作者banna
相关产品推荐
相关产品推荐

