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

React中useRef统计渲染次数首次变更从1跳至3的原因及解决方法

问题原因及修复方案

原因分析

  1. 开发环境下React Strict Mode的双重执行机制
    React在开发环境的Strict Mode中,会对组件渲染逻辑、useEffect回调进行两次调用,目的是检测代码中是否存在不可重复执行的副作用。这是开发环境专属的调试行为,生产环境不会触发。
  2. 无依赖的useEffect导致每次渲染都执行
    你的代码中useEffect没有设置依赖数组,意味着组件每次渲染完成后都会执行该effect。结合Strict Mode的双重渲染,每次组件更新时,effect会被额外执行一次,导致计数多增加了1次。

具体到你的场景:

  • 初始挂载后,renderCount因Strict Mode的两次useEffect执行从1变为2,但页面仍显示1(因为useRef的变化不会触发组件重渲染)。
  • 首次输入触发组件更新时,Strict Mode再次强制组件双重渲染+useEffect双重执行,最终让renderCount从1直接跳到3。

修复方案

方案1:直接在组件函数体中统计渲染次数(推荐)

组件每执行一次就代表一次渲染,直接在组件函数内递增计数,无需依赖useEffect,结果更准确:

import React, { useRef, useState } from 'react';
const UseRef = () => {
    const [name, setName] = useState('');
    const renderCount = useRef(0);

    // 每次组件渲染时递增计数
    renderCount.current += 1;

    return (
        <>
            <input value={name} onChange={e => setName(e.target.value)} />
            <div>My name is {name}</div>
            <div>I rendered {renderCount.current} times</div>
        </>
    );
};

export default UseRef;

注:开发环境下Strict Mode仍会让计数多一次,但这是正常的调试行为,生产环境会自动恢复正确计数。

方案2:给useEffect添加依赖数组

如果你需要仅在状态更新时计数,可以给useEffect添加依赖数组,限制其执行时机:

import React, { useEffect, useRef, useState } from 'react';
const UseRef = () => {
    const [name, setName] = useState('');
    const renderCount = useRef(1);
    // 标记是否为开发环境下Strict Mode的首次执行
    const isFirstEffectRun = useRef(true);

    useEffect(() => {
        // 跳过Strict Mode的第一次重复执行
        if (isFirstEffectRun.current) {
            isFirstEffectRun.current = false;
            return;
        }
        renderCount.current += 1;
    }, [name]); // 仅当name变化时执行

    return (
        <>
            <input value={name} onChange={e => setName(e.target.value)} />
            <div>My name is {name}</div>
            <div>I rendered {renderCount.current} times</div>
        </>
    );
};

export default UseRef;

方案3:临时关闭Strict Mode(不推荐)

若只是开发时不想看到该现象,可以在项目入口文件(如index.js)中移除<React.StrictMode>标签。但不建议这么做,因为Strict Mode能帮你提前发现代码中的潜在副作用问题。

内容的提问来源于stack exchange,提问作者Pagla gamer

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.19 18:53:20