useState初始值不要直接使用该值

AFA*_*FAF 1 typescript reactjs react-hooks react-typescript

我有一个初始状态,我从不直接在代码中使用,只在另一个设置值状态中使用

仅举一个草稿示例:

interface PersonProps {}

const Person: React.FC<PersonProps> = () => {
  const [name, setName] = useState<string>("")
  const [todayYear, setTodayYear] = useState<string>("")
  const [birthYear, setBirthYear] = useState<string>("")
  const [age, setAge] = useState<string>("")

  const getPerson = async () => {
    try {
      const response = await getPersonRequest()
      const data = await response.data

      setName(data.name)
      setTodayYear(data.today_year)
      setBirthYear(data.future_year)
      setAge(data.todayYear - data.birthYear)
    } catch (error) {
      console.log(error)
    }
  }

  useEffect(() => {
    getPerson()
  })


  return (

    <h1>{name}</h1>
    <h2>{age}</h2>
  )

}
export default Person
Run Code Online (Sandbox Code Playgroud)

在这种情况下,如您所见,我永远不会在 UI 上使用“ todayYear ”和“ birthYear ”,因此代码会发出警告

TodayYear 被分配了一个值但从未使用过

我可以做什么来解决这个问题和/或忽略这个警告?

T.J*_*der 5

如果您不使用它们进行渲染,则没有理由将它们放在您的状态中:

const Person: React.FC<PersonProps> = () => {
    const [name, setName] = useState<string>("")
    const [age, setAge] = useState<string>("")
  
    const getPerson = async () => {
        try {
            const response = await getPersonRequest()
            const data = await response.data
      
            setName(data.name)
            setAge(data.todayYear - data.birthYear)
        } catch (error) {
            console.log(error)
        }
    }
  
    useEffect(() => {
        getPerson()
    })
  
    return (
        <h1>{name}</h1>
        <h2>{age}</h2>
    )
}
Run Code Online (Sandbox Code Playgroud)

旁注:在大多数情况下,您可以在useState提供初始值时省略类型参数。两者之间没有区别:

const [name, setName] = useState<string>("")
Run Code Online (Sandbox Code Playgroud)

const [name, setName] = useState("")
Run Code Online (Sandbox Code Playgroud)

TypeScript 将从参数推断类型。仅当推理无法进行时,您才需要明确,例如如果您有useState<Thingy | null>(null).


正如另一个答案指出的那样,除非您希望每次组件重新渲染时都运行代码(这将导致无限渲染循环),否则您需要指定一个依赖项数组。在这种情况下,如果您只想获取一次人员信息,则可能为空。

另外,由于您的组件有可能在异步操作发生之前被卸载,因此如果它卸载,您应该取消您的个人请求(或者至少忽略卸载的结果):

const Person: React.FC<PersonProps> = () => {
    const [name, setName] = useState<string>("");
    const [age, setAge] = useState<string>("");
  
    const getPerson = async () => {
        const response = await getPersonRequest();
        const data = await response.data;
        return data;
    };
  
    useEffect(() => {
        getPerson()
        .then(data => {
            setName(data.name)
            setAge(data.todayYear - data.birthYear)
        })
        .catch(error => {
            if (/*error is not a cancellation*/) {
                // (Probably better to show this to the user in some way)
                console.log(error);
            }
        });
        return () => {
            // Cancel the request here if you can
        };
    }, []);
  
    return (
        <h1>{name}</h1>
        <h2>{age}</h2>
    );
};
Run Code Online (Sandbox Code Playgroud)

如果无法取消getPersonRequest,则后备是一个标志:

const Person: React.FC<PersonProps> = () => {
    const [name, setName] = useState<string>("");
    const [age, setAge] = useState<string>("");
  
    const getPerson = async () => {
        const response = await getPersonRequest();
        const data = await response.data;
        return data;
    };
  
    useEffect(() => {
        let mounted = true;
        getPerson()
        .then(data => {
            if (mounted) {
                setName(data.name)
                setAge(data.todayYear - data.birthYear)
            }
        })
        .catch(error => {
            // (Probably better to show this to the user in some way)
            console.log(error);
        });
        return () => {
            mounted = false;
        };
    }, []);
  
    return (
        <h1>{name}</h1>
        <h2>{age}</h2>
    );
};
Run Code Online (Sandbox Code Playgroud)