React理论知识总结

React总结

React技术栈 概述

React简介
  • 是一个用于构建用户界面的 JavaScript 库
  • 主要用于构建UI
  • 性能较高,代码逻辑简单
React特点
  • JSX — JS语法的扩展
  • 声明式设计
  • 高效 — 虚拟DOM,提高复用,减少与DOM的交互
  • 灵活 —与已知的库或框架配合
  • 组件 — 容易复用
  • 单向响应的数据流 — 减少重复代码,父组件到子组件
相关技术
  • React Native —— 原生移动应用
  • React VR —— 虚拟应用程序
React安装
  • 利用React脚手架工具

    •      构建工具(webpack - 模块打包机)
              cd <fileName> --进入到某一个文件内
              cd..  -返回上一层文件夹
              npm init (-y) 项目初始化
              npm i webpack webpack-cli -g  -g是全局安装
              npm install <packageName> == npm i <packageName>
              npm i <pname> --save-dev == npm i <pname> -D 安装开发依赖
              npm i <pname>  后面不加参数,默认是项目依赖
              卸载:npm uninstall <packageName>
         
              打包
              npm i webpack webpack-cli --save-dev
              npm i webpack webpack-cli -g
              
              webpack-dev server  html-webpack-plugin
              监听代码的变化,实时构建
         
              配置命令 
              package.json 中,在 scripts 配置 start
              以后启动项目执行 npm start
      
    •    创建React项目过程
         npx create-react-app my-app
         cd my-app
         npm start
      

React基础语法

JSX语法
  • JSX
    • JavaScript 和 XML 结合的一种格式

    • 利用 HTML 语法来创建虚拟 DOM

    • 实例

      React操作的是数据
      插值表达式
       const root = ReactDOM.createRoot(
         document.getElementById('root')
       );
      
       1、字符串
      const title = "React";
      
      2、新的React元素
      const title = {<span>hello</span>}
      
      3、三目运算符
      const title = {100>50?txt:"200"}
       
       4、函数调用
       const renderTxt = (txt) => {
        return txt;
      }
      const ele=<span>{renderTxt("React")}</span>
       
      const ele = <span>{title}</span>;
      root.render(ele);
      
  • React元素 —— 实际为一个普通对象
  • Babel编译(将声明式的代码转成对象)
    • 把 JSX 转换成 React.createElement( ) 调用,返回 JS 对象
    • React.createElement( type, props, …children )
元素渲染
  • ”根“DOM节点

  • 元素渲染

    • 将 React 元素传递给 ReactDOM.render( ) 渲染到页面上
  • 更新渲染元素

    • React元素不可变,创建后无法改变内容和属性
    • DOM比较算法
  • 条件渲染(三目运算符/短路操作)

    • const flag = false;
      const ele = flag ? <div>react</div> : null  //切换元素
      const ele2 = flag && <div>react</div>  //是否显示
      
  • 循环渲染

    • 1、
      const list = (
        <ul>{[<li>111</li>, <li>111</li>]}</ul>
      )
      
      2、
      const data = [111, 222, 333, 444, 555, 666]
      const list = (
          <ul>{data.map(item => <li>{item}</li>)}</ul>
      )
      
      root.render(list);
      
组件
  • 组件

    • React组件是可复用的小代码片段
    • 返回React元素用于渲染页面
    • 类定义、函数定义
  • 函数定义组件

    • 快捷生成代码:rafce

    • 接收props对象,返回React元素

    • props

      • 从父组件传给子组件的属性
      • 只读
      • 名称大写字母开头
      • 验证使用的是 PropTypes,传入数据无效时抛出警告
      • 类组件默认含有,直接this.props使用
      • 函数组件只是为了呈现,无法写具体功能;类组件可以写具体功能
    • eg:

      1、
      function App() {
        return (
          <div>
            <header>
              ddd
            </header>
          </div>
        );
      }
      2、
      const App = ()=>{
        return <h1>Hello React{props.data}</h1>
      }
      
      export default App;
      
      props应用:
      const App=(props)=>{
        console.log(props);
        return <h1>
            title:{props.title}
            id:{props.id}
        </h1>;
      }
      const root = ReactDOM.createRoot(
        document.getElementById('root')
      );
      root.render(<App title="React" id="100"/>)
      
  • 类定义组件

    • React.Component :React内的抽象基础类

    • 继承React.Component 方式使用

    • 至少定义一个render()

    • 类组件基础语法举例

      • class Hello extends React.Component { 
        	render( ) { 
        		return <h1>Hello</h1>; 
        	} 
        }
        
  • State

    • 私有的、完全受控于当前组件,组件外部无法修改

    • 类定义组件特有属性

    • 状态声明(构造函数是唯一能够初始化 this.state 的地方 )

      • constructor( ){    
        	super();  
        	this.state = {name:’React’}
        }
        super传递props,在constructor中才能获取到this.props
        
        constructor(){	
            super();//把父级this传给子类,务必先写
            //super 传递props,在constructor中才能获取到this.props
            this.state = { type: "类" }
            setTimeout(() => {
              this.setState({ type: "函数" })
            }, 2000
        }
        
      • 直接state={}

  • 生命周期函数

    • 某一个时刻组件会自动执行的函数
    • 类定义的组件中才有
    • 阶段
      • 初始化 —— constructor( )
        • 装载前被调用
        • 在任何其他的表达式之前调用super(props)
        • 作用:
          • 初始化状态,通过赋值一个对象到 this.state
          • 绑定事件处理函数到一个实例
      • 挂载
        • static getDerivedStateFromProps( ) —— 实例化后或接受新属性时调用

        • render() —— 类组件唯一、必须的方法

        • componentDidMount( ) —— 挂载后调用,发送请求 (fetch请求)

          • fetch('https://cnodejs.org/api/v1/topics')
            	.then(res => res.json())
            	.then(res =>res.data ))//这里获取的data是一个数组,里面是对象
            
      • 更新
        • static getDerivedStateFromProps( )
        • shouldComponentUpdate( ) —— 渲染前调用
        • render()
        • getSnapshotBeforeUpdate( ) —— 渲染提交前调用,返回值作为传参
        • componentDidUpdate( )
      • 卸载 —— componentWillUnmount( )
      • 错误 —— componentDidCatch( )
事件处理
  • 事件绑定

    • 属性命名:驼峰式写法
    • 传入一个函数作为事件处理函数
  • 事件处理函数绑定this

    • bind绑定

      • 绑定事件后 .bind(this)
    • 箭头函数

      • const renderTxt = (txt) => {
          return txt;
        }
        const renderTxt = (txt) => txt;
        const renderTxt = t => {return t};
        const renderTxt = t => t;
        
    • 传参

      • 函数声明时事件对象作为最后一个参数传入

        • onClick={(e) => this.show(id, e)}
          e 为事件对象
          
      • 箭头函数的事件对象显示传入;bind 会隐式传入

        • onClick={this.show.bind(this, id)}
          
受控组件和非受控组件
  • 受控组件
    • React控制输入值的表单元素
    • setState( )方法更新可变状态
  • 非受控组件
    • 数据在DOM中
    • defaultValue :指定初始值
    • refs :获取表单的值
  • refs
    • 访问在 render 方法中创建的 DOM 节点或 React 元素
    • 适用
      • 处理焦点、文本选择或媒体控制
      • 触发强制动画
      • 集成第三方 DOM 库
      • 可以声明式实现,尽量避免使用 refs
DOM Elements
  • React实现了一套与浏览器无关的 DOM 系统
  • className
  • onChange —— 处理输入
  • htmlFor
  • dangerouslySetInnerHTML —— 相当于innerHTML
  • style —— 小驼峰命名;接收JS对象
PropTypes —— 类型检查
defaultProps —— 设置默认值

组件间交互

  • 父组件向子组件通信
    • 直接属性来传,在子组件调用this.props.函数名/参数名
  • 子组件向父组件通信
    • 直接传值无法实现
    • 父组件传给子组件一个更新值的方法,子组件通过调用方法更新值
  • 状态提升 —— 传函数子传父/传参父传子
    • 两个子组件之间数据传递需要状态提升
    • 当有多个组件需要使用相同的数据时,将这份数据提升到两子组件的共同父组件中进行管理
  • 跨级组件间通信:使用 context 对象
    • 实现跨越多层级交互
    • 通过组件树提供了传递数据的方法 ,避免逐层手动传递props
    • API
      • React.createContext —— 创建上下文对象
      • Provider —— 提供状态;只出现一次
      • Consumer —— 获取状态
    • 单独一个Context.js文件设置,用来放全局的状态
  • 非嵌套组件间通信
    • 利用二者共同父组件的 context 对象进行通信
    • 使用自定义事件的方式

HOC(高阶组件)

  • 重用组件逻辑
  • 是一个函数,接收一个组件作为参数,返回新组件

Hooks

  • Hook是React 16.8新增特性

  • 在不编写 class 的情况下使用 state 以及其他 React 特性

  • 使用规则

    • 只在最顶层使用 Hook
    • 只在 React 函数中调用 Hook
  • 基础Hooks Api —— 只能用于函数组件

    • useState —— 声明状态,可以多个

      • 会将最新状态的值赋给初始值

      • const [num, setNum] = useState(0);
        num为参数,setNum为操作方法
        
      •  const [plants, setPlants] = useState([]);
         setPlants(
            plants.map(item => {
                if (item.plantID == plant.plantID) {
                     return {
                        ...item,
                         isCollect: !item.isCollect
                   }
                }
         	    return item;
            })
           )
        
      • 为数组对象添加属性

      <button>{item.isCollect 
          ? "已收藏" 
          : "收藏"}
      </button>
      按钮名称改变
      
    • useContext —— 组件树功能

    • useEffect

      • 异步操作,定时器等

      • 操作有副作用的代码

      • 代替生命周期

        • componentDidMount
        • componentDidUpdate:每次更新执行,return挂载执行完后执行
        • componentWillUnmount
      • useEffect(()=>{
                ...
         },[num])
         表示在num发生变化时执行
         不写参数,只执行一次,相当于ComponentDidMount、componentDidUpdate
        
    • useReducer

      • const initState={
            num:0,
            val:"",
            list:[]
        }
        const reducer=(state,action)=>{}
        
        const [state, dispatch] = useReducer(reducer,initState);
        
         const add =()=>{
             dispatch({type:"add+1"})
          })
        
        • dispatch :派发更新
        • action:是一个对象,必须有一个type属性,描述更新的内容
        • reducer:是一个纯函数,记录着状态更新的规则
    • useCallback

      • 用来缓存一个函数,仅在某个依赖项改变时才会更新
      • 用法同useEffect(()=>{},[])
    • useMemo

      • const memoizedValue =useMemo(callback,array)
        
      • callback是一个函数用于处理逻辑

      • array 控制useMemo重新执⾏行的数组,array改变时才会 重新执行useMemo

        • 不传数组,每次更新都会重新计算
        • 空数组,只会计算一次
        • 依赖对应的值,当对应的值发生变化时,才会重新计算(可以依赖另外一个 useMemo 返回的值)
      • useMemo的返回值是一个记忆值,是callback的返回值

      • 优点

        • 减少不必要的DOM循环和子组件渲染
    • useRef

      • 存储不需要引起页面渲染的数据

      • 返回值是一个可变的ref对象

      • 修改useRef值的唯一方法是修改.current

      •  const inputEle = useRef();
             const add = () => {
                console.log(inputEle.current.value);
             }
             return <div>
                 <input ref={inputEle} type="text" />
                 <button onClick={add}>添加</button>
             </div>
        

虚拟DOM与性能优化

虚拟DOM
  • 介绍
    • 编程概念
    • 用于表示视图的对象
    • 采用React的声明式API
    • fiber对象来存储dom结构,差分算法diff可用于更新元素
  • 优点
    • 提升性能
    • 实现跨端应用
  • 差分算法(diff)
    • 同级比对但意义不大
    • 比对发生在state发生变化时
性能优化
  • 利用key值提升性能

  • PureComponent

    • React提供的类
    • 比较前后props,state,不变则不渲染
  • memo

    • memo会比较组件前后的props,如果没有变化就不更新
  • 类组件可用memo和PureComponent
    函数组件只可用memo,因为没有state,函数组件改变状态使用useState
    
  • useMemo

  • useCallback

React路由

路由配置
  • React 路由

    • react-router 是浏览器和原生应用的通用部分
    • react-router-native 是用于原生应用的
    • react-router-dom 是用于浏览器的
  • 安装

    • npm install --save react-router-dom
    • npm i react-router-dom@5.3.0
  • 引入

    • import { BrowserRouter as Router,Route,Link} from 'react-router-dom';
      ……
      class Hello extends React.Component { 
      	render( ) { 
      		return (
      			<Router>  
      				<div>
      					<Route exact path='/' component={Home}/>
      					<Route path='/about' component={About}/>
      				</div>
      			</Router>
      		); 
      	} 
      }
      
  • BrowserRouter VS HashRouter

    • 都是路由的基本组件,需将其放在最外层
    • BrowserRouter 的 URL 是指向真实 URL 的资源路径,页面和浏览器的 history 保持一致
    • HashRouter 使用 URL 中的 hash(#)部分去创建路由
    • Router在整个项目中只会出现一次(一般最外层)
    • 匹配路径、挂载组件

    • <Route exact  path='/home'  component={ Home }/>
      
       exact : 严格匹配  在匹配 /home 时不会再匹配到 / 的内容
       path : 字符串类型,用来匹配url
       component : 值是一个组件,在 path 匹配成功后挂载这个组件
      
    • Route放在哪里切换哪里

  • <Redirect to = “…” >

    • 当被挂载时,将路由重定向为 to 属性指定的地址

      • <Route path="/home" render={( )=><Redirect to="/other“ />}/>
        
    • from 和 exact 两个属性只能用在 组件下的 < Redirect />

      • <Switch>
        	<Redirect from = '/old‘  to = ‘/new‘ />
        	<Route path='/new' component={ New }/>
        </Switch>
        
  • <Switch > … </Switch>

    • 只会挂载与 路径匹配成功的第一个

    • 子节点只能是 或

    • 为根路径精准匹配,防止出现其他页面的同时渲染根路径内容;先写长的

    • <Route component={()=><h1>您访问的页面不存在</h1>}/>
      在Switch中加入这样一项路由匹配,防止都匹配失败时显示首页
      任何路径不存在时显示页面
      
  • <Link to = “…” > … </Link>

    • <Link to="/home">Home</Link>
      点击改变地址栏地址
      
      通过Link改变地址,Route在监听地址栏,以此改变页面,二者没有直接关联
      
      Link为a标签
      
  • <NavLink to = “…” > … </NavLink>

    • NavLink 是 Link 的子类
    • activeClassName:string,被选中时添加的类名
    • activeStyle:object,被选中时添加的行内样式
    • exact:boolean,严格匹配
动态路由
  • 路由内挂载的组件,是拥有四个属性(history、location、match、[[Prototype]]

    对象)的对象

  • 数据接收

    • match

      • 包含** **匹配路径参信息的对象
      • params、url、path、isExact
    • location.search

      • 数据存放在 this.props.location.search

      • 通过 URL 模块解析

        • npm install url –save
          url.parse(urlStr : string,parseQueryStr : true)
          
    • 数据获取举例

    1、
    Link内可以传参数
    <Link to="/?a=100&id=200">Home</Link>
    通过props.location.search拿到
    从而兄弟组件之间可以路由传递数据
    
    2、
    const NewsDetail = (props) => {
      return <div>
        {props.match.params.id}
      </div>
    }
     <Route path="/news/:id" component={NewsDetail} />
     <Link to="news/1">News1</Link>
    
    通过props.match.params.id 拿到id
    
路由Hooks
  • 两种引入组件方式
    1、
    <Route path="/" component={Home} />
    2、不具备props的四个属性
     <Route path="/">
        <Home />
     </Route>
    
  • useHistory

    • import {useHistory} from "react-router-dom";
      
      const history = useHistory();
      
  • useLocation

    • import { useLocation} from "react-router-dom";
      
      const location = useLocation();
      
  • useRouteMatch

  • useParams

    • import {useParams} from "react-router-dom";
      
      const params = useParams();
      
  • 优点

    • 引入所需要的对象即可,避免通过props引入四个对象
封装好的代码组件
  • Axios

    • 安装:npm i axios

    • 文档用法:https://www.axios-http.cn/

    • 使用方式:
      	axios.get("xx")
       	   .then(res=>{})
      eg:
      	import axios from 'axios';
          const baseURL = 'xx';
          export const getPlants = () => {
              return axios.get(`${baseURL}/getPlants`)
          }
          export const getA = () => {
              return axios.get(`${baseURL}/aaaa`)
          }
      
      	在其他组件内调用:
      	引入:import { getPlants } from '...'
      	获得res值:
      		getPlants()
                  .then(res => {
                      setPlants(res.data.result.plantList)
              })
      
  • Ant design

    • 安装:npm i antd
    • 文档
      • https://ant.design/
      • https://mobile.ant.design/
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值