You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React useEffect依赖缺失警告与无限循环问题求助

问题解决:React useEffect依赖警告与无限循环问题

问题描述

我编写了一个过滤函数,借助state变量data、dataCopy和searchValue实现数据过滤。当前遇到的问题是:如果不将data加入useEffect的依赖数组,React会抛出“React Hook useEffect has a missing dependency: 'data'”的警告;但如果将data加入依赖数组,又会因useEffect内部修改了data状态而触发无限循环。

核心问题分析

当前写法错误地用useEffect处理过滤逻辑,且在useEffect内修改data状态——这会形成依赖循环:修改data触发useEffect重新执行,useEffect又再次修改data,最终导致无限循环。

实际上,过滤操作属于纯计算逻辑,完全不需要依赖useEffect触发,直接基于原始数据dataCopy和搜索条件searchValue实时计算即可。

解决方案

步骤1:移除处理搜索的useEffect

删掉用于触发过滤的useEffect,避免依赖循环和不必要的状态更新。

步骤2:将过滤后的数据改为计算值(用useMemo优化性能)

保留dataCopy作为原始数据的唯一存储,过滤后的数据通过dataCopy和searchValue实时计算,无需单独存为state。如果数据量较大,用useMemo缓存计算结果,避免重复渲染损耗性能。

修改后的完整代码

import React, { useEffect, useState, useMemo } from 'react'
import Header from '../Components/Header/Header'
import Home from '../Components/Home/Home'
import "./Layout.css"
import Spinner from '../Components/Spinner/Spinner'
import axios from 'axios' // 补全原代码遗漏的axios导入

function Layout() {
    // 原始数据与加载状态
    const [dataCopy, setDataCopy] = useState([])
    const [spinner, setSpinner] = useState(true) // 补全原代码遗漏的spinner状态

    // 搜索输入状态
    const [searchValue, setSearchValue] = useState("")

    // 更新搜索值
    const changeSearchValue = (value) => {
        setSearchValue(value)
    }

    // 计算并缓存过滤后的数据
    const filteredData = useMemo(() => {
        if (searchValue === "") {
            return dataCopy
        }
        return dataCopy.filter(item =>
            !isNaN(searchValue) 
                ? item.expected_annually_bill_amount.toString().includes(searchValue) 
                : item.dmo_content.Ausgrid.toString().toLowerCase().includes(searchValue.toLowerCase())
        )
    }, [searchValue, dataCopy])

    // API请求获取原始数据
    useEffect(() => {
        axios.post(`${process.env.REACT_APP_BASE_URL}`, { data: "" },
            {
                headers:
                {
                    'Api-key': `${process.env.REACT_APP_API_KEY}`,
                },
            })
            .then((response) => response.data.data.token)
            .then((tokenIs) => {
                return axios.post(`${process.env.REACT_APP_DATA_URL}`,
                    { "session_id": `${process.env.REACT_APP_SESSION_ID}` },
                    {
                        headers:
                        {
                            'Api-key': `${process.env.REACT_APP_API_KEY}`,
                            'Auth-token': tokenIs,
                        },
                    })
            })
            .then((response) => {
                setDataCopy(response.data.data.electricity)
                setSpinner(false)
            })
            .catch((err) => {
                setSpinner(false)
                alert(err)
            })

    }, [])


    return (
        <>
            {spinner ? <Spinner /> : null}
            <div className='layout'>
                <Header
                    changeSearchValue={changeSearchValue}
                    searchValue={searchValue}
                />
                <Home data={filteredData} />
            </div>
        </>
    )
}

export default Layout

额外说明

  • 补全了原代码遗漏的axios导入和spinner状态定义。
  • 用useMemo包裹过滤逻辑,仅在searchValue或dataCopy变化时重新计算,优化渲染性能。
  • 这种写法彻底消除了useEffect的依赖问题,逻辑更清晰:原始数据仅在API请求时更新,过滤后的数据是纯计算结果。

内容的提问来源于stack exchange,提问作者Sharanjeet Singh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 13:05:25