简体   繁体   English

如何在useState hook React中异步设置状态

[英]How to asynchronously set state in useState hook React

I want to change var value, which is initialized with useState hook after some timeout.我想更改 var 值,该值在超时后使用useState钩子初始化。 What is proper way to achieve this?实现这一目标的正确方法是什么? That's my try:这是我的尝试:

const [msg, setMsg] = useState("Hello");

  const changeMsg = () => {
    return new Promise((resolve, reject) => {
      setTimeout(() => {
        resolve("Buy");
      }, 1000);
    });
  };

  useEffect(() => {
    setMsg(async () => {
      const res = await changeMsg();
      return res;
    });
  }, []);

Sandbox 沙盒

You can achieve this with this code:您可以使用以下代码实现此目的:

import { useEffect, useState } from "react";
import "./styles.css";

export default function App() {
  const [msg, setMsg] = useState("Hello");

  const changeMsg = () => {
    return new Promise((resolve, reject) => {
      setTimeout(() => {
        resolve("Buy");
        setMsg("Another Value");
      }, 1000);
    });
  };

  useEffect(() => {
    changeMsg();
  }, []);

  return <div className="App">Message is: {msg}</div>;
}

The value for variable msg change after 1 second to Another value.变量 msg 的值在 1 秒后更改为另一个值。

Since the other answer and the solution in the comments are missing a rather important thing, here's my take on the problem:由于评论中的另一个答案和解决方案缺少一个相当重要的东西,这是我对这个问题的看法:

    const [msg, setMsg] = useState("Hello");

    useEffect(()=>{
        const timeout = setTimeout(()=>{
            setMsg("Buy");
        }, 1000);
        return ()=>clearTimeout(timeout);
    }, []); //only run on first render

    return (
        <div className="App">Message is: {msg}</div>
    )

Whenever you are using something asynchronous in an effect hook, you should provide a cleanup function.每当你在一个效果钩子中使用异步的东西时,你应该提供一个清理函数。 Even here, where the hook runs only once.即使在这里,钩子只运行一次。

Why?为什么? Because otherwise you get an error if the component is unmounted before the timeout ran.因为否则,如果在超时运行之前卸载组件,则会出现错误。

 import React , {useState,useEffect} from 'react' import "./styles.css"; export default function App (){ const [msg,setMsg] = useState("Hello"); useEffect(() => { const clear = setTimeout(() => setMsg("Busy"),2000); return () => {clearTimeout(clear)} },[]) return(<div> <h1>{msg}</h1> </div>) }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM