useState和回调函数

14
在类组件中,setState()方法可以接受回调函数。但是在函数式组件中,当我为自定义的 setState 方法提供一个回调时,会出现以下警告: 警告:来自useState()useReducer() Hook 的状态更新不支持第二个回调参数。要在渲染后执行副作用,请在组件主体中声明它使用 useEffect()。 我需要设置我的状态,然后页面将会重定向。但我没有任何想法。

2
你所收到的警告实际上是在试图给你一个思路。你可以使用 useEffect 来解决这个问题。 - devserkan
1
嗨,如果您想要更明确的答案,请随时分享任何困扰您的代码,我们将能够更好地帮助您。 - JamesGill
如果您的函数组件仍然保持类组件,那么有什么特别需要注意的吗? - tareq aziz
@devserkan 我该如何在这种情况下使用useEffect? - S. Hesam
@tareqaziz 我必须使用函数式组件。 - S. Hesam
@techguru 我已经接受了。 - S. Hesam
2个回答

15

不要传递callback函数,而是使用useEffect钩子,按照以下方式进行操作以实现所需的结果。

 useEffect(() => {
    console.log('state changed', your-state-variable)
    // write your callback function here
  }, [your-state-variable]);

0

小心!在类组件中,您可以在每个想要的setState之后立即调用回调函数,但在函数式组件中,useEffect钩子会在整个组件中发生任何状态更改后运行。

为了应对这个挑战,您应该仔细选择您的状态以及如何设置它。

是一个非常简单的例子:

import { Grid, Button, Typography } from "@material-ui/core";
import { Component, useState, useEffect } from "react";

export const FunctionComponent = () => {
  const [count, setCount] = useState(0);
  const [background, setBackground] = useState("white");

  useEffect(() => {
    setTimeout(() => setBackground("white"), 100);
  }, [background]);

  const countIncreamentHandler = () => {
    setCount((count) => count + 1);
    setBackground("rgba(112, 181, 0, .2)");
  };
  const countDecreamentHandler = () => {
    setCount((count) => count - 1);
    setBackground("rgba(181, 9, 0, .2)");
  };

  return (
    <Grid container justify="space-around">
      <Button
        variant="contained"
        color="primary"
        onClick={countIncreamentHandler}
      >
        +
      </Button>
      <Typography style={{ padding: 5, background }} variant="h5">
        {count}
      </Typography>
      <Button
        variant="contained"
        color="secondary"
        onClick={countDecreamentHandler}
      >
        -
      </Button>
    </Grid>
  );
};

在类组件中:
export class ClassCompontet extends Component {
  constructor() {
    super();
    this.state = {
      count: 0,
      background: "white"
    };
  }

  countIncreamentHandler = () => {
    this.setState(
      (prevState) => ({
        count: prevState.count + 1,
        background: "rgba(112, 181, 0, .2)"
      }),
      () => {
        setTimeout(() => {
          this.setState({ background: "white" });
        }, 100);
      }
    );
  };
  countDecreamentHandler = () => {
    this.setState(
      (prevState) => ({
        count: prevState.count - 1,
        background: "rgba(181, 9, 0, .2)"
      }),
      () => {
        setTimeout(() => {
          this.setState({ background: "white" });
        }, 100);
      }
    );
  };

  render() {
    return (
      <Grid container justify="space-around">
        <Button
          variant="contained"
          color="primary"
          onClick={this.countIncreamentHandler}
        >
          +
        </Button>
        <Typography
          style={{ padding: 5, background: this?.state?.background }}
          variant="h5"
        >
          {this?.state?.count}
        </Typography>
        <Button
          variant="contained"
          color="secondary"
          onClick={this.countDecreamentHandler}
        >
          -
        </Button>
      </Grid>
    );
  }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接