美文网首页
react hook入门

react hook入门

作者: dream_Q | 来源:发表于2020-02-25 15:40 被阅读0次

    一、react hook介绍

    Hook 是 React 16.8 的新增特性。它可以让你在不编写 class 的情况下使用 state 以及其他的 React 特性。目的是解决React的状态逻辑复用问题,因为React Hooks只共享数据处理逻辑,并不会共享数据本身。

    在React应用开发中,状态管理是组件开发必不可少的内容。以前,为了对状态进行管理,最通常的做法是使用类组件或者直接使用redux等状态管理框架。现在,开发者可以直接使用React Hooks提供的State Hook来处理状态。

    众所周知,React提供了两种创建组件的方式,即函数组件和类组件。函数组件是一个普通的JavaScript函数,接受props对象并返回React元素,函数组件更符合React数据驱动视图的开发思想。不过,函数组件缺乏类组件诸如状态、生命周期等种种特性,而Hooks的出现就是让函数式组件拥有类组件的特性。

    为了让函数组件拥有类组件的诸如状态、生命周期等特性,React 提供了3个核心的api,即state hook 、Effect hook以及自定义 hook。

    二、react hook的使用方法

    import React, { useState } form 'react';

    function Example() {

        // useState 方法返回一个数组。第一个值是当前的 state,第二个值是更新 state 的函数,相当于类组件的setState。

        const [count, setCount] = useState(0);

        return (

            <div>

                <p>You clicked {count} times</p>

                <button onClick={() => setCount(count + 1)}>点我加1</button>

            </div>

      );

    }

    如上示例,这个函数组件有自己的状态,并且还可以更新自己的状态。useState用于创建一个新的状态,参数为一个固定的值(初始值,作为useState的参数来将其初始化为 0)或者一个有返回值的方法。执行后的结果为一个数组,分别为生成的状态count以及改变该状态的方法setCount,通过解构赋值的方法拿到对应的值与方法。

    函数组件中如果存在多个状态,既可以通过一个useState声明对象类型的状态,也可以通过useState多次声明状态。

    const [count, setCount] = useState({

      count1: 0,

      count2: 0

    });

    或者

    const [count1, setCount1] = useState(0);

    const [count2, setCount2] = useState(0);

    三、Effect hook 的使用方法

    Effect Hook 可以在函数组件中执行副作用操作,主要用于以下两种情况:

    1.函数式组件中不存在传统类组件生命周期的概念,如果我们需要在一些特定的生命周期或者值变化后做一些操作的话,必须借助useEffect的一些特性去实现。

    2.useState产生的 changeState 方法并没有提供类似于setState的第二个参数一样的功能,因此如果需要在 State 改变后执行一些方法,必须通过useEffect实现。

    该钩子接受两个参数,第一个参数为副作用需要执行的回调,生成的回调方法内可以返回一个函数(将在组件卸载时运行);第二个为该副作用监听的状态数组,当对应状态发生变动时会执行副作用,如果第二个参数为空,那么在每一个 State 变化时都会执行该副作用。

    const [count, changeCount] = useState(0);

    // 将在count变化时打印最新的count数据

    useEffect(()=> {

      message.info(`count发生变动,最新值为${count}`);

    }, [count])

    在上面的例子中,我们实现了利用useState实现了setState后执行某个方法,那如果想要实现componentDidMount和componentWillUnmout生命周期的功能呢?

    首先所有的副作用在组件挂载完成后会执行一次 ,如果副作用存在返回函数,那么返回的函数将在卸载时运行。我们要做的就是让与该副作用相关联的状态为空数组,不管其他状态如何变动,该副作用都不会再次执行,于是就实现了componentDidMount和componentWillUnmout。

    functionChild({ visible }){

      useEffect(()=> {

        message.info('我只在页面挂载时打印');

        return ()=> {

          message.info('我只在页面卸载时打印');

        };

      }, []);

      return visible ? 'true' : 'false';

    }

    在上面示例中,我们实现了componentDidMount和componentWillUnmout,那么如何实现componentDidUpdate呢?其实,只要第二个参数为空(注意不是上面示例中的空数据,而是不传第二个参数),那么在每一个 State 变化时都会执行该副作用了。

    useEffect(()=> {

     ……

    })

    四、如何自定义Hook

    众所周知,要在类组件之间共享一些状态逻辑是非常麻烦的,常规做法是通过高阶组件或函数的属性来解决。不过,新版的React允许开发者创建自定义Hook来封装共享状态逻辑,且不需要向组件树中增加新的组件。

    所谓的自定义Hook,其实就是指函数名以use开头并调用其他Hook的函数,自定义Hook的每个状态都是完全独立的。

    export const useAxios = (url, dependencies) => {

        const [isLoading, setIsLoading] = useState(false);

        const [response, setResponse] = useState(null);

        useEffect(() => {

            setIsLoading(true);

            axios.get(url).then((res) => {

                setIsLoading(false);

                setResponse(res);

            }).catch((err) => {

                setIsLoading(false);

            });

        }, dependencies);

        return [isLoading, response, error];

    };

    使用自定义方法:

    function Example() {

      let url = 'http://www.baidu.com/api/xxx';

      const [isLoading, response, error] = useAxios(url, []);

      ...

    }

    export default Example;

    五、使用Hooks的注意事项:

    1.不要在循环、条件或嵌套函数中使用Hook,并且只能在React函数的顶层使用Hook。因为React需要利用调用顺序来正确更新相应的状态,以及调用相应的生命周期函数函数。一旦在循环或条件分支语句中调用Hook,就容易导致调用顺序的不一致性,从而产生难以预料到的后果。

    2.只能在React函数式组件或自定义Hook中使用Hook。

    参考链接:https://segmentfault.com/a/1190000019438921

    相关文章

      网友评论

          本文标题:react hook入门

          本文链接:https://www.haomeiwen.com/subject/ytstchtx.html