React 限制渲染次数以防止无限循环...重新渲染次数过多

Posted

技术标签:

【中文标题】React 限制渲染次数以防止无限循环...重新渲染次数过多【英文标题】:React limits the number of renders to prevent an infinite loop...Too many re-renders 【发布时间】:2021-12-25 18:38:11 【问题描述】:

如何避免无限循环问题?

渲染以下组件时出现错误:

重新渲染过多。 React 限制了渲染的数量以防止无限循环。?

TeamContent.js 多次重新渲染,如何在加载时设置初始渲染?

Error given

TeamContent.js

import  useEffect, useRef  from "react";
import  useDispatch, useSelector  from "react-redux";
import 
  fetchTeamPlayers,
  fetchUpcomingGames,
  fetchPreviousGames,
  fetchLiveGames,
 from "../../../data/UserInfo/infoActions";
import TeamPlayers from "./TeamPlayers";
import TeamNext from "./TeamNext";
import TeamPrevious from "./TeamPrevious";
import LiveEvent from "./Live.js/LiveEvent";

function TeamContent(props) 
  console.log("test");
  let containsLiveGame = false;
  const dispatch = useDispatch();
  const liveGames = useSelector((store) => store.userInfo.live.games.all);
  const status = useSelector((store) => store.userInfo.playersLoadStatus);
  const UpcomingGamesstatus = useSelector(
    (store) => store.userInfo.upcomingGamesStatus
  );
  const previousGamesStatus = useSelector(
    (store) => store.userInfo.previousGamesStatus
  );
  const liveStatus = useSelector((store) => store.userInfo.live.games.status);

  liveGames.map((game) => 
    const verifyHomeTeam = +game.idHomeTeam === +props.teamID;
    const verifyAwayTeam = +game.idAwayTeam === +props.teamID;

    if (verifyAwayTeam || verifyHomeTeam) 
      containsLiveGame = true;
    
  );

  // -----> request team data
  useEffect(() => 
    dispatch(fetchTeamPlayers(props.teamID));
    dispatch(fetchUpcomingGames(props.teamID));
    dispatch(fetchPreviousGames(props.teamID));
    dispatch(fetchLiveGames());
  , [dispatch, props.teamID]);

  useEffect(() => 
    dispatch(fetchLiveGames());

    const interval = setInterval(() => 
      dispatch(fetchLiveGames());
    , 30000);

    return () => clearInterval(interval);
  , [dispatch]);

  return (
    <div className="teamDash">
      <div className="dashLeft">
        <div
          className="dashLeftHead"
          style=
            backgroundImage: `url($props.stadiumImg)`,
          
        >
          <div className="dashLeftHeadAbs"></div>
          <div className="dashLeftHeadIntro">
            <span>props.stadiumName</span>
            <h3>props.teamName</h3>
          </div>
        </div>
        liveStatus !== "error" && containsLiveGame && <LiveEvent />

        status !== "error" && (
          <div className="dashLeftPlayers">
            <TeamPlayers />
          </div>
        )

        <div className="dashLeftDesc">
          <p>props.teamDesc</p>
        </div>
      </div>
      <div className="dashRight">
        UpcomingGamesstatus === "error" ? (
          console.log("unable to load upcoming games")
        ) : (
          <div className="upcomingGames">
            <TeamNext id=props.teamID />
          </div>
        )
        previousGamesStatus === "error" ? (
          console.log("unable to load previous games")
        ) : (
          <div className="previousGames">
            <TeamPrevious />
          </div>
        )
      </div>
    </div>
  );


export default TeamContent;

infoActions.js

import  API_URL  from "../Api";
import  infoActions  from "./infoSlice";

export function fetchTeams() 
  return (dispatch) => 
    dispatch(infoActions.loadStatusHandler( status: "loading" ));
    async function getTeams() 
      try 
        const rq = await fetch(`$API_URLLookup_all_teams.php?id=4387`);
        const res = await rq.json();
        const data = res.teams;
        dispatch(infoActions.loadTeamsHandler( teams: data ));
        dispatch(infoActions.loadStatusHandler( status: "done" ));
       catch (error) 
        dispatch(infoActions.loadStatusHandler( status: "error" ));
      
    
    getTeams();
  ;


export function fetchTeamPlayers(id) 
  return (dispatch) => 
    async function getPlayers() 
      dispatch(infoActions.statusPlayersHandler( status: "loading" ));
      try 
        const rq = await fetch(`$API_URLlookup_all_players.php?id=$id`);
        const res = await rq.json();
        const data = res.player;
        dispatch(infoActions.loadPlayersHandler( players: data ));
        dispatch(infoActions.statusPlayersHandler( status: "done" ));
       catch (error) 
        dispatch(infoActions.statusPlayersHandler( status: "error" ));
      
    
    getPlayers();
  ;


export function fetchUpcomingGames(id) 
  return (dispatch) => 
    dispatch(infoActions.statusUGHandler( status: "loading" ));
    async function getGames() 
      try 
        const rq = await fetch(`$API_URLeventsnext.php?id=$id`);
        const res = await rq.json();
        const data = res.events;
        dispatch(infoActions.upcomingGamesHandler( games: data ));
        dispatch(infoActions.statusUGHandler( status: "done" ));
       catch (error) 
        dispatch(infoActions.statusUGHandler( status: "error" ));
      
    
    getGames();
  ;


export function fetchPreviousGames(id) 
  return (dispatch) => 
    dispatch(infoActions.statusPGHandler( status: "loading" ));
    async function getGames() 
      try 
        const rq = await fetch(`$API_URLeventslast.php?id=$id`);
        const res = await rq.json();
        const data = res.results;
        dispatch(infoActions.previousGamesHandler( games: data ));
        dispatch(infoActions.statusPGHandler( status: "done" ));
       catch (error) 
        dispatch(infoActions.statusPGHandler( status: "error" ));
      
    
    getGames();
  ;


export function fetchLiveGames() 
  return (dispatch) => 
    dispatch(infoActions.statusLiveGames( status: "loading" ));
    async function getGames() 
      try 
        const rq = await fetch(
          `https://www.thesportsdb.com/api/v2/json/40130162/livescore.php?l=4387`
        );
        const res = await rq.json();
        const data = res.events;
        dispatch(infoActions.statusLiveGames( status: "done" ));
        dispatch(infoActions.loadLiveGames( liveGames: data ));
       catch (error) 
        dispatch(infoActions.statusLiveGames( status: "error" ));
      
    
    getGames();
  ;

【问题讨论】:

尽量不要使用代码截图,在问题代码中贴出错误 【参考方案1】:

尝试从您传递给的数组中删除dispatch

useEffect(() => 
...
, [dispatch, props.teamID])

useEffect(() => 
...
, [dispatch])

dispatch 是一个函数,如果你将它包含到useEffect 监听器中,useEffect 将在每次渲染时触发

【讨论】:

加载时仍然出现同样的错误 通过注释掉代码中的所有 useEffect 来尝试逐步调试

以上是关于React 限制渲染次数以防止无限循环...重新渲染次数过多的主要内容,如果未能解决你的问题,请参考以下文章

收到此错误:错误:重新渲染过多。 React 限制渲染次数以防止无限循环

我有一个错误:重新渲染太多。 React 限制渲染次数以防止无限循环

为啥错误:重新渲染太多。 React 限制了渲染的数量以防止无限循环。?

太多的重新渲染。 React 限制了渲染的数量以防止无限循环。?

错误:重新渲染过多。 React 限制了渲染的数量以防止无限循环。即使使用箭头函数

..Use state error: Too many re-renders React 限制渲染次数以防止无限循环