react hooks的应用&&react-router-dom hooks的应用

react hooks的应用

useContext(context)

import React, { useContext } from 'react'
const bgcolor = {
    bgf: {background: "red"},
    bgs: {background: "blue"}
}
const themeContext = React.createContext(bgcolor.bgf);//创建以bgcolor.bgf为默认值context上下文

export default function ReactHook() {
    return (
        <div>
            <themeContext.Provider value={bgcolor.bgs}>//提供值bgcolor.gbs给包含的组件以及后代组件
                <Test />
            </themeContext.Provider>
        </div>
    )
}
function Test() {
    return (
        <div>
            直接使用useContext返回值(第一种):<ThemedButton />
            <br />
            <hr />
            <br />
            直接使用themeContext.Consumer返回值(第二种):<ThemedButtonConsumer />
            <br />
            <hr />
            <br />
            直接使用ReactHook.contextType(static)返回值(第三种):<ThemedButtonStatic />
            <br />
            <hr />
            <br />
            直接使用ReactHook.contextType(class)返回值(第四种):<ThemedButtonClass />
        </div>
    )
}
//第四种
class ThemedButtonClass extends React.Component {
    componentDidMount() {
        console.log(this.context)
    }
    render() {
        return (
            <div style={{ background: this.context.background }}>
                ReactHook.contextType
            </div>
        )
    }
}
ThemedButtonClass.contextType = themeContext;

//第三种
class ThemedButtonStatic extends React.Component {
    static contextType = themeContext;
    componentDidMount() {
        console.log(this.context)
    }
    render() {
        return (
            <div style={{ background: this.context.background }}>
                ReactHook.contextType
            </div>
        )
    }
}
//第二种
function ThemedButtonConsumer() {
    return (
        <div>
            <themeContext.Consumer>
                {value => {
                    console.log(value)
                    return (
                        <div style={{ background: value.background }}>
                            consumer
                        </div>
                    )
                }}
            </themeContext.Consumer>
        </div>
    )
}
//第一种
function ThemedButton() {
    const contextV = useContext(themeContext)
    console.log(contextV);
    return (<div style={{ background: contextV.background }}>usecontext</div>)
}

结果:如下图所示
在这里插入图片描述

useReducer

import React,{useReducer} from 'react'
const initstate={count:0}
const reducer=(state,action)=>{
    switch(action.type){
        case 'add':
            return {count:state.count+1}
        case 'reduce':
            return {count:state.count - 1}
        default:
            return state.count
    }
}
export default function UseReducerTest() {
   const [state, dispatch] = useReducer(reducer, initstate); 
   console.log(state,dispatch);
    return (
        <div>
             <button onClick={()=>{dispatch({type:'add'})}}>+</button>
            {state.count}
            <button onClick={()=>{dispatch({type:'reduce'})}}>-</button>
           
        </div>
    )
}

useMemo(调用函数并返回其结果)

原因:

  1. class组件调用setState,无论state的值是否改变都会触发组件重新渲染,可以通过shouldComponentUpdate比较前后state的值是否发生变化,通过return false阻止更新。
  2. 函数组件中,react不再区分挂载跟更新两个状态,这意味着函数组件的每一次调用都会执行其内部的所有逻辑,那么会带来较大的性能损耗。所以通过useMemo跟useCallback解决这个问题。
//没有添加useMemo之前,改变name,ChangeAge函数会被触发

import React, { useState, useMemo } from 'react'
export default function UseMemoDemo() {
    const [age, setAge] = useState(18);
    const [name, setName] = useState('lili');
    const ChangeAge = () => {
        console.log('change age1');
        return <div>age1:{age}</div>
    }
    return (
        <div>
            <button onClick={() => {
                setAge(age + 1)
            }}>改变age</button>
            <button onClick={() => {
                setName('dd')
            }}>改变name</button>
            <ChangeAge1 />
            {name}:{age}
        </div>
    )
}



//添加了useMemo,之后
import React, { useState, useMemo } from 'react'
export default function UseMemoDemo() {
    const [age, setAge] = useState(18);
    const [name, setName] = useState('lili');
    
    const ChangeAge = useMemo(() => {//函数在初始化的时候会执行,其后,只有当依赖项age改变的时候,ChangeAge函数才会执行
        console.log('age change')
        return <div>age:change{age}</div>
    }, [age])
    
    const ChangeName = useMemo(() => {//函数在初始化的时候会执行,其后,当依赖项name改变的时候,ChangeName函数才会执行
        console.log('name change');
        return <div>name:{name}</div>
    }, [name])
    return (
        <div>
            <button onClick={() => {   //改变age的值
                setAge(age + 1)
            }}>改变age</button>
            {name}:{age}
            
            <button onClick={() => {   //改变name的值,多次点击这个函数,但ChangeName也最多只能执行一次,因为name在点击一次之后值修改为tom,其后点击name的值不变。
                setName('tom')
            }}>改变name</button>

 			<input type="text" value={name}  //输入值,可以改变name的值,每次输入都能触发ChangeName函数
 				placeholder="改变name" 
 				onChange={e=>{setName(e.target.value)
 			}}/>
        </div>
    )
}

useCallback ( 返回函数而不调用)

import React,{useState,useCallback} from 'react'

export default function UseCallbackdemo() {
    const [age, setAge] = useState(18)
    const [name, setName] = useState('lili');
    const c = useCallback(  //当age的值发生改变时,才会返回新的函数
        () => {
            console.log('调用了函数c');
        },
        [age],
    )
    return (
        <div>
            <Header c={c} />
            <button onClick={() => { setAge(age + 1) }}>changeAge</button>
            <button onClick={() => { setName('dd') }}>changeName</button>
            {name}:{age}
        </div>
    )
}
function Header(props){
    const {c}=props;
    console.log('render')
    return <p onClick={c} style={{color:'red'}}>change</p>
}
Header=React.memo(Header); //React.memo 仅检查 props 变更,当 state 或 context 发生变化时,它仍会重新渲染。

函数组件的useRef跟类组件的React.createRef()

useRef
import React, { useRef } from 'react'
export default function UseRefdemo() {
    const ref = useRef('');
    return (
        <div>
            <input type="text" ref={ref} />
            <button onClick={() => {
                ref.current.focus()
                console.log(ref.current.value);
            }}>点击</button>
        </div>
    )
}

React.createRef()
import React, { Component } from 'react'
export default class UseRefdemo extends Component {
    constructor(props){
        super(props);
        this.inputref=React.createRef();
    }
    render() {
        return (
            <div>
              <input type="text" ref={this.inputref}/>
              <button onClick={()=>{
                  this.inputref.current.focus()
                  console.log(this.inputref.current.value)
              }}>获取焦点</button>
            </div>
        )
    }
}

参考链接

https://blog.csdn.net/qq_39081974/article/details/114380881?utm_medium=distribute.pc_relevant.none-task-blog-2defaultbaidujs_baidulandingword~default-1.no_search_link&spm=1001.2101.3001.4242.2

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值