首页 > 其他分享 >前端React篇之React Hook 的理解及实现原理

前端React篇之React Hook 的理解及实现原理

时间:2024-03-20 14:30:57浏览次数:20  
标签:函数 前端 React Hook useState 组件 useEffect

目录


React Hook 的理解及实现原理

React Hook是React16.8引入的新特性,它可以让函数组件拥有类似于class组件中的state和生命周期等特性,以及更好地复用状态逻辑。使用Hook可以在不编写class的情况下,为函数式组件引入状态和副作用。

  1. useState: useState Hook 可以让你在函数式组件中添加局部的 state 状态。
  2. useEffect: useEffect Hook 可以让你在函数式组件中执行副作用操作,比如数据获取、订阅管理等。
  3. 自定义Hook: 通过使用自定义Hook,可以将一些常见的逻辑进行封装,使得它们可以被多个组件共享。

实现原理

React Hook的实现原理基于JavaScript闭包和Fiber架构。当函数组件每次执行时,Hook会根据调用顺序和依赖关系来确定当前组件的状态,并保持这些状态的独立性。useState和useEffect等Hook存储在Fiber节点上的Hooks链表中,React在渲染过程中根据这些Hook的信息来安排组件的更新和副作用的执行。

类组件 vs 函数组件

  1. 类组件:使用 class 关键字定义的组件,继承自 React.Component。这种形式下,我们可以通过定义 state 和生命周期方法来管理组件的状态和行为。

    class DemoClass extends React.Component {
      state = {
        text: ""
      };
      componentDidMount() {
        //...
      }
      changeText = (newText) => {
        this.setState({
          text: newText
        });
      };
    
      render() {
        return (
          <div className="demoClass">
            <p>{this.state.text}</p>
            <button onClick={this.changeText}>修改</button>
          </div>
        );
      }
    }
    
  2. 函数组件:使用简单的函数形式定义的组件。早期它无法维护状态,因此被称为“无状态组件”。相比类组件,函数组件更轻量、灵活,并且易于维护。

    function DemoFunction(props) {
      const { text } = props;
      return (
        <div className="demoFunction">
          <p>{`函数组件接收的内容:[${text}]`}</p>
        </div>
      );
    }
    

为什么需要 Hooks

在过去,函数组件的能力相对有限,无法使用状态或生命周期方法等功能,因此我们无法完全使用函数组件来构建复杂的应用。React Hooks 的出现就是为了解决这些问题。

React Hooks 解决了什么问题

  1. 状态管理:通过 useState Hook,我们可以在函数组件中使用状态。
  2. 副作用处理:使用 useEffect Hook 可以替代生命周期方法,处理数据获取、订阅等副作用。
  3. 逻辑复用:自定义 Hook 允许我们将组件之间共享的逻辑提取到可重用的函数中。

案例1.tsx

import React, { useState, useEffect } from 'react';

interface DemoFunctionProps {
  // 定义组件的 props 类型
}

const DemoFunctionWithHooks: React.FC<DemoFunctionProps> = (props) => {
  const [text, setText] = useState<string>("");

  useEffect(() => {
    // 相当于 componentDidMount 和 componentDidUpdate
    // 处理副作用
  }, [/* 依赖项 */]);

  const changeText = (newText: string) => {
    setText(newText);
  };

  return (
    <div className="demoFunction">
      <p>{text}</p>
      <button onClick={() => changeText("新文本")}>修改</button>
    </div>
  );
}

export default DemoFunctionWithHooks;

在这个案例中,我们创建了一个名为 DemoFunctionWithHooks 的函数组件。它使用了 useState 来定义 text 这个状态变量,并使用 setText 函数来更新文本。通过 useEffect 可以处理副作用,类似于类组件中的 componentDidMountcomponentDidUpdate。在按钮点击时,调用 changeText 函数来更新文本内容。

案例2.tsx

import React, { useState, useEffect } from 'react';

// 模拟异步数据获取
const fetchData = () => {
  return new Promise<string>(resolve => {
    setTimeout(() => {
      resolve("数据");
    }, 1000);
  });
};

function Counter() {
  const [count, setCount] = useState(0);
  const [data, setData] = useState<string | null>(null);

  useEffect(() => {
    fetchData().then(response => setData(response));
  }, []);

  return (
    <div>
      <p>Count: {count}</p>
      <button onClick={() => setCount(count + 1)}>Increment</button>
      {data && <p>Data: {data}</p>}
    </div>
  );
}

export default Counter;

在这个案例中,我们定义了一个名为 Counter 的函数组件。它使用了 useState 来定义 countdata 这两个状态变量,并使用 setCountsetData 函数来更新这些状态。同时,通过 useEffect,在组件加载后会执行数据获取操作,并将获取的数据存储到 data 状态中。当用户点击按钮时,count 状态会加一。

注意:

  • 在使用 useEffect 时,需要注意传递的依赖项数组。如果依赖项发生变化,useEffect 将会重新运行。
  • 在使用多个状态时,可以多次调用 useState 来定义不同的状态变量。

总结

React Hooks 提供了一种全新的方式来组织和管理 React 组件的状态和副作用逻辑,使得函数组件具备了更强大的能力。其实现原理基于 Fiber 架构和 JavaScript 闭包,通过 Hooks 链表来管理组件的状态和副作用。合理使用 Hook 可以帮助开发者更好地组织和复用组件逻辑,提高代码可读性和可维护性。

在实际应用中,React Hooks 提供了一种新的方式来编写 React 组件,使得函数组件具备了类组件的状态管理和副作用处理能力。通过 Hooks,我们能够更方便地编写清晰、简洁且易于测试的组件代码。当我们需要在函数组件中使用状态、生命周期方法或者其他 React 特性时,可以考虑使用相应的 Hook 来实现。这样可以让代码更加模块化,易于理解和维护,同时也能更好地促进组件逻辑的复用。

持续学习总结记录中,回顾一下上面的内容:
React Hooks 是一种让函数组件拥有状态和副作用处理能力的特性。它的实现原理基于 React 的 Fiber 架构和 JavaScript 的闭包机制,通过 Hooks 链表来管理组件的状态和副作用。使用 Hooks 可以让我们更方便地编写清晰、简洁且易于维护的组件代码,提高代码的可读性和可维护性。

标签:函数,前端,React,Hook,useState,组件,useEffect
From: https://blog.csdn.net/qq_37255976/article/details/136812519

相关文章

  • 前端必学-40个精选案例实战-案例9:企业首页实战项目【PC端网页布局】
    项目首页.psd项目设计图头部导航条的制作资源:html,body,div,span,applet,object,iframe,h1,h2,h3,h4,h5,h6,p,blockquote,pre,a,abbr,acronym,address,big,cite,code,del,dfn,em,img,ins,kbd,q,s,samp,small,strike,strong,sub,sup,tt,......
  • 19.html+css网页设计实例/“美妆”口红主题介绍/web前端期末大作业/
    前言本文以“美妆”口红网页为主题设计,本实例系统文件种类包含:html结构文件、css网页样式文件。应用DIV、点击事件、表格、搜索等,供大家参考。【关注作者|获取更多源码(2000+个Web案例源码)|优质文章】;您的支持是我创作的动力!看到这里就【点赞收藏博文】,三连支持下吧,3Q!有兴趣的......
  • 前端防止重复提交案例
    前端防止5秒内重复提交案例:varisBusy=0if(isBusy==1){errorMsg("5秒钟内不能重复提交!");returnfalse;}else{isBusy=1;setTimeout(functi......
  • Vue前端界面的创建和路由的配置
    大纲:创建vue文件并访问*创建vue文件,在views目录创建文件*在文件的template节点中添加要显示的内容*在route目录下的index.js文件中配置路由    *使用import引入vue文件        *配置路由    {        path:'/url',     ......
  • 前端路由history路由和hash路由的区别?原理?
    前端路由是指在单页应用程序(SPA)中通过改变URL路径来实现页面切换和导航的机制。在前端开发中,有两种主要的前端路由实现方式:基于HistoryAPI的路由(history-basedrouting)和基于哈希(Hash)的路由(hash-basedrouting)。基于HistoryAPI的路由(history-basedrouting):Histor......
  • 前端基础之JavaScript的数据类型
    一、常用的调试语句方法说明示例归属alert(msg);警告,在浏览器中弹出一个警告框,内容为alert里面的内容alert("Surprise");浏览器closole.log(msg);控制台,在控制台内输出一些内容console.log("Surprise");浏览器prompt(问题,值);对话框,第一个参数是询问内......
  • 前端基础之JavaScript引入
    一、什么是JavaScriptJavaScript是一门跨平台、面向对象的脚本语言(不需要编译,直接解释运行即可),来控制网页的行为,它能使网页可交互。脚本语言:不需要编译,运行过程中由js解释器(js引擎)逐行来进行解释并执行。现在也可以基于Node.js技术进行服务器端编程W3C标准:网页主要由......
  • 前端性能优化
    性能优化的目的是为了实现资源的快速加载和响应。性能优化前,需要先分析性能,目的是分析出包含页面渲染、网络传输和文件加载等时间指标,对该页面进行评估分析。找出影响性能的主要因素和瓶颈,对此给出性能优化解决方案。1.性能分析Chrome浏览器的Performance选项卡主要用于对页......
  • react的生命周期函数
    react的生命周期函数1.react所有的生命周期函数https://react.docschina.org/docs/react-component.html挂载当组件实例被创建并插入DOM中时,其生命周期调用顺序如下:constructor()staticgetDerivedStateFromProps()render()componentDidMount()更新当组件......
  • 关于前端的学习2
    目录前言:1.标签的进阶:1.1单标签:功能标签1.2双标签:内容标签1.3元标签(MetaTags):1.3.1标题(Title):1.3.2描述(Description):1.3.3关键词(Keywords):1.3.4其他元标签:1.4链接标签:1.4.1锚文本(AnchorText):1.4.1Nofollow属性:1.5图片标签:1.5.1Alt属性:1.5.1Title属性:1.6结构......