React Hooks 钩子特性
人在身处逆境时,适应环境的能力实在惊人。人可以忍受不幸,也可以战胜不幸,因为人有着惊人的潜力,只要立志发挥它,就一定能渡过难关。
Hooks 是 React 16.8 的新增特性。它可以让你在不编写 class 组件的情况下使用 state 以及其他的 React 特性。
React Hooks 表现形式是以 use 开头的函数被称为 Hook。useState 是 React 提供的一个内置 Hook。你可以在 React API 参考 中找到其他内置的 Hook。你也可以通过组合现有的 Hook 来编写属于你自己的 Hook。
跟普通函数相比,Hook 比普通函数更为严格。你只能在你的组件(或其他 Hook)的顶层调用 Hook。如果你想在一个条件或循环中使用 useState,请提取一个新的组件并在组件内部使用它。
为什么要使用 Hooks?
- 解决高阶类组件复用,导致代码层级复杂问题。
- React 组件生命周期的复杂,用于代替生命周期函数。
- 如果一个类一开始设计成了 function 组件,无状态组件,因为需要状态,又改成了 class 成本高。
1. State Hook
State 让组件“记住”用户输入之类的信息。例如,表单组件可以使用 state 来存储输入值,而图片库组件可以使用 state 来存储所选的图像索引。要给组件添加状态,可以使用以下介绍的钩子之一。
1.1 useState
useState 是一个 React Hook。它允许你向组件添加一个状态变量。模拟类组件的状态管理。
// usss
const [state, setstate] = usestate(initialState)
1.2 useReducer
useReducer 是一个 React Hook,它允许你向组件里面添加一个 reducer,来维护一个状态 state。useReducer 不支持异步处理,异步处理需要借助于 Hooks useEffect。
在单个组件中实现状态管理,理解 useReducer 的使用。
const [state, dispatch] = useReducer(reducer, initialState)
其次配合 useContext 跨级通信。将数据逻辑(即状态管理)从组件中(视图逻辑)分离出来通过外部管理,降低组件耦合度。对于单个组件来说意义不大,但是对于多个组件数据需要共享状态的时候很方便。
2. Context Hook
2.1 useContext
useContext 是一个 React Hook,可以让你读取和订阅组件中的 context。减少组件层级,便于组件跨级通信处理。
useContext 配合 useState、useContext 配合 useReducer。
3. Ref Hooks
Refs 允许组件保存一些不用于呈现(渲染)的信息,比如 DOM 节点或超时 ID。与 state 不同,更新 ref 并不会重新呈现组件。React 提供了 useRef hook 来描述。
3.1 useRef
保存引用值:
const ref = useRef(initialValue)
4. Effect Hooks
Effect 允许组件 连接到外部系统并与之同步。这包括处理网络、浏览器、DOM、动画、使用不同 UI 库编写的 widgets 以及其他非 React 代码。
Effect Hooks 副作用钩子函数很好模拟了类组件的生命周期函数。但是我们知道 Function Component 不存在生命周期,所以不要把 Class Component 的生命周期概念搬过夹试图对号入座。
4.1 useEffect
useEffect 是一个 React Hook,它允许你 连接到外部系统并与之同步。
useEffect(setup, dependencies?)
// 处理副作用
useEffect(() => {
// 副作用函数处理代码块 { 比如数据请求,定时器 }
console.log("effect")
return () => {
console.log("cleanup")
// cleanup
// 执行时机:无依赖情况下:组件销毁执行 有依赖情况下:依赖更新和组件销毁的时候
}
}, [ name /* 依赖的状态,如果为空表示不依赖任何状态 */])
依赖:不要对 Dependencies 撒谎,如果你明明在 effect 中使用了某个变量,却没有申明在依赖中,你等于向 React 撒了谎,后果就是,当依赖的变量改变时,useEffect 也不会再次执行,eslint 会报警告。
4.2 useLayoutEffect
useLayoutEffect 是 useEffect 的一个版本,在浏览器重新绘制屏幕之前触发。useLayoutEffect 内部的代码和所有计划的状态更新阻塞了浏览器重新绘制屏幕。如果过度使用,这会使你的应用程序变慢。如果可能的话,尽量选择 useEffect。
然后如果 Effect 一定要阻止浏览器绘制屏幕,使用 useLayoutEffect 替换 useEffect。请注意,绝大多数的 Effect 都不需要这样。只有当在浏览器绘制之前运行 Effect 非常重要的时候才需要如此:例如,在用户看到 tooltip 之前测量并定位它。
4.3 useInsertionEffect
useInsertionEffect 是为 CSS-in-JS 库的作者特意打造的。除非你正在使用 CSS-in-JS 库并且需要注入样式,否则你应该使用 useEffect 或者 useLayoutEffect。
4.4 Effect Hooks 之间区别
简单来说就是调用时机不同,useLayoutEFfect 和原来 componentDidMount & componentDidUpdate 一致,在 React 完成 Dom 更新后马上同步调用的代码,即在浏览器重新绘制屏幕之前触发 useLayouteEffect。你可以在这里测量布局。会阻塞页面渲染(渲染树)。
useEffect 是会在整个页面渲染完才会调用的代码。
useInsertionEffect 会在 React 修改 DOM 之前触发。可以在这里插入动态 CSS。
官方建议优先使用 useEffect
However, we recommend starting with useEffect first and only trying useLayoutEffect if that causes a problem.
在实际使用时如果想避免页面抖动(即在 useEffect 里修改 Dom 很有可能出现)的话,可以把需要操作 Dom 的代码放在 useLayoutEffect 里。在这里做点 Dom 操作,这些 Dom 修改会和 react 做出的更改一起被一次性渲染到屏幕上,只有一次回流、重绘的代价。

5. 性能 Hook
5.1 useMemo
useMemo 是一个 React Hook,它在每次重新渲染的时候能够缓存、使用计算的结果。
const cachedValue = useMemo(calculateValue, dependencies)
useMemo(() => first, [second])
记忆纯函数计算结果、跳过组件的重新渲染,记忆一个函数。
对于使用 useMemo 记忆一个函数,这看起来很笨拙!记忆函数很常见,React 有一个专门用于此的内置 Hook。将你的函数包装到 useCallback 而不是 useMemo 中,以避免编写额外的嵌套函数。 即 useCallback 的唯一好处是它可以让你避免在内部编写额外的嵌套函数。它没有做任何其他事情。
5.2 useCallBack
useCallback 是一个允许你在多次渲染中缓存函数的 React Hook。记忆函数,防止因为组件重新渲染,导致组件内部定义的方法被重新创建,起到缓存作用。只有第二个参数依赖项变化了才重新声明一次。如果依赖传入空数组,那么函数第一次创建后就被缓存,这时如果函数定义中的使用了某个状态值改变了,以后调用函数拿到的还是老的值。如果不传第二个参数,每次都会重新声明一次。
const cachedFn = useCallback(fn, dependencies)
和 useMemo 唯一的区别是:useCallback 不会执行第一个参数函数,而是将它返回给你,而 useMemo 会执行第一个参数函数并且将函数执行结果返回给你。所以在前面的例子中,可以返回 handleClick 来达到存储函数的目的。
所以 useCallback 常用记忆事件函数,生成记忆后的事件函数并传递给子组件使用。而 useMemo 更适合经过函数计算得到一个确定的值,比如记忆组件、结果。
5.3 useTransition
useTransition 允许将状态转换标记为非阻塞,并允许其他更新中断它此更新。
5.4 useDeferredValued
useDeferredValue 是一个 React Hook,可以让你延迟更新 UI 的某些部分。
6. 资源 Hook
use 是一个 React Hook,它可以让你读取类似于 Promise 或 context 的资源的值。
7. 其他 Hook
这些 Hook 主要对库作者有用,而不常用于应用程序代码。
useDebugValue 允许在 React 开发者工具中为自定义 Hook 添加一个标签。
useId 允许组件绑定一个唯一 ID,其通常与可访问性 API 一起使用。
useSyncExternalStore 允许一个组件订阅一个外部 store。
8. 自定义 Hooks
当我们想在两个函数之间共享逻辑时,我们会把它提取到第三个函数中。即抽离复用 js 逻辑,让结构更加清晰,符合函数式编程思想。
必须以 'use' 开头吗?必须如此。这个约定非常重要。不遵循的话,由于无法判断某个函数是否包含对其内部 Hook 的调用,React 将无法自动检查你的 Hook 是否违反了 Hook 的规则。官网主要研究以下几个问题:
- 什么是自定义钩子,如何编写自己的钩子;
- 如何命名和结构化自定义的钩子;
- 何时以及为什么要提取自定义钩子;
- 如何在组件之间重用逻辑;
React Hooks 钩子特性的更多相关文章
- React Hooks新特性学习随笔
React Hooks 是 React 16.8 的新增特性.它可以让你在不编写 class 的情况下使用 state 以及其他的 React 特性. 前言 本篇主要以讲几个常用的api为主. 1.u ...
- 使用React Hooks新特性useReducer、useContext替代传统Redux高阶组件案例
当我们使用redux进行数据管理的时候,一般都是在根组件通过Provider的方式引入store,然后在每个子组件中,通过connect的方式使用高阶组件进行连接,这样造成的一个问题是,大量的高阶组件 ...
- React Hooks用法大全
前言 在 React 的世界中,有容器组件和 UI 组件之分,在 React Hooks 出现之前,UI 组件我们可以使用函数,无状态组件来展示 UI,而对于容器组件,函数组件就显得无能为力,我们依赖 ...
- react新特性 react hooks
本文介绍的是react新特性react hooks,本文面向的是有一定react开发经验的小伙伴,如果你对react还不是很熟悉的话我建议你先学习react并多多联系. 首先我们都知道react有3种 ...
- 30分钟精通React今年最劲爆的新特性——React Hooks
你还在为该使用无状态组件(Function)还是有状态组件(Class)而烦恼吗? --拥有了hooks,你再也不需要写Class了,你的所有组件都将是Function. 你还在为搞不清使用哪个生命周 ...
- 关于React Hooks,你不得不知的事
React Hooks是React 16.8发布以来最吸引人的特性之一.在开始介绍React Hooks之前,让咱们先来理解一下什么是hooks.wikipedia是这样给hook下定义的: In c ...
- 如何构建自己的 react hooks
我们组的前端妹子在组内分享时谈到了 react 的钩子,趁此机会我也对我所理解的内容进行下总结,方便更多的同学了解.在 React 的 v16.8.0 版本里添加了 hooks 的这种新的 API,我 ...
- React Hooks究竟是什么呢?
摘要: React Hooks原理解析. 原文:快速了解 React Hooks 原理 译者:前端小智 我们大部分 React 类组件可以保存状态,而函数组件不能? 并且类组件具有生命周期,而函数组件 ...
- React Hooks简单业务场景实战(非源码解读)
前言 React Hooks 是React 16.7.0-alpha 版本推出的新特性.从 16.8.0 开始,React更稳定的支持了这一新特性. 它可以让你在不编写 class 的情况下使用 st ...
- React hooks详解
此篇文章仅是对hooks入门的总结,老鸟略过吧~ React从16.8.X以后增加了一个新特性,react hooks 让我们看看这个新特性又带来了哪些惊喜呢~以下内容我们采取不同方式创建组件来进行对 ...
随机推荐
- 带你上手基于Pytorch和Transformers的中文NLP训练框架
本文分享自华为云社区<全套解决方案:基于pytorch.transformers的中文NLP训练框架,支持大模型训练和文本生成,快速上手,海量训练数据>,作者: 汀丶 . 1.简介 目标: ...
- 《SQLi-Labs》02. Less 6~10
@ 目录 索引 Less-6 题解 原理 Less-7 题解 Less-8 题解 Less-9 题解 原理 Less-10 题解 sqli.开启新坑. 索引 Less-6:布尔盲注,字符型[" ...
- 《SQL与数据库基础》20. 主从复制
目录 主从复制 原理 搭建 主库配置 从库配置 测试 本文以 MySQL 为例 主从复制 主从复制是指将主数据库的 DDL 和 DML 操作通过二进制日志传到从库服务器中,然后在从库上对这些日志重新执 ...
- 通过 Haproxy 实现 ss 负载均衡
介绍 缺点:所有的SS的加密方式和密码必须一致 介绍:HAProxy是一个使用C语言编写的自由及开放原始码软件,其提供高可用性.负载均衡,以及基于TCP和HTTP的应用程序代理. 安装Haproxy ...
- linux中的sar命令
linux中的sar命令 sar命令的安装 [root@localhost test]# yum install sysstat 安装成功! sar命令说明 语法格式 sar [ 选项 ] [ < ...
- Docker系列——介绍、安装、镜像、容器、docker容器与镜像、数据卷、Dockerfile、docker 配置pycharm连接
目录 1 Docker 介绍 1.1 简介 1.2 Docker平台介绍 1.3 为什么使用Docker 2 Docker 整体结构(了解) 2.1 Docker引擎介绍 (Docker Engine ...
- MySQL中sql_mode的设置
在升级MySQL版本到8.0的过程中,需要关注sql_mode参数默认值的变化,8.0版本sql_mode不支持 NO_AUTO_CREATE_USER,要避免配置的sql_mode中带有 NO_AU ...
- 从内核世界透视 mmap 内存映射的本质(源码实现篇)
本文基于内核 5.4 版本源码讨论 通过上篇文章 <从内核世界透视 mmap 内存映射的本质(原理篇)>的介绍,我们现在已经非常清楚了 mmap 背后的映射原理以及它的使用方法,其核心就是 ...
- splay + 垃圾回收 知识点与例题的简要讲解
splay 简要讲解 前置芝士:普通二叉树 splay tree是一个越处理越灵活的数据结构,通过splay(伸展)操作,使整棵树的单次查询时间复杂度接近于O(log n),整棵树的高度也接近于log ...
- Redis 6 学习笔记 3 —— 用SpringBoot整合Redis的踩坑,了解事务、乐观锁、悲观锁
SpringBoot整合Redis时踩到的坑 jdk1.8环境,用idea的Spring Initializr创建spring boot项目,版本我选的2.7.6.pom文件添加的依赖如下,仅供参考. ...