React

1.基礎(chǔ)的React

1.1 Context與ContextType

Context提供了一種方式,能夠讓數(shù)據(jù)在組件樹中傳遞而不必一級一級的手動傳遞,但會讓組件失去獨立性。


context結(jié)構(gòu)

API:createContext(defaultValue?)

import {createContext} from 'react'
const BatteryContext = createContext()

<BatteryContext.Provider value={}>
</BatteryContext.Provider>

<BatteryContext.Consumer>
{
    battery=><h1>{battert}</h1>
}
</BatteryContext.Consumer>

static  contextType = BatteryContext
render(){
    const battery = this.context
}

1.2 lazy與Suspense

暫時沒有資源展示---->延遲加載:

  • Webpack - Code Splitting
    把一個頁面人為的劃分為模塊進行導(dǎo)入
  • import
    1.做靜態(tài)模塊導(dǎo)入
    import 。。。 from
    2.動態(tài)模塊導(dǎo)入
    import('').then(...)
    typeof import
    webpack就會做一次代碼拆分,把import的依賴打包成一個獨立的文件,默認情況下,不會馬上加載它,只有用到的時候才會導(dǎo)入。指組件渲染的時候。封裝的是組件導(dǎo)入的行為,而不是組件本身。而且導(dǎo)入意味著網(wǎng)絡(luò)請求。
const About = lazy=(()=>import(/*webpackChunkName:'about'*/'./about.jsx'))

lazy的返回就是一個組件
用了lazy后,會存在一個加載中的空檔,不知道什么時候加載
這時候用Suspense

<Suspense fallback=(<div>About</div>)>
    <About>
    </About>
</Suspense>

block request url阻止獲取請求(當(dāng)出現(xiàn)加載錯誤的時候,suspense不能捕獲,但錯誤邊界可以)

//ErrorBoundary錯誤邊界
componentDidCatch(){
  this.setState({
  hasError:true
})
}
//一旦發(fā)生錯誤,就返回一個新的state數(shù)據(jù),并合并到新的state之中
static getDerivedStateFromError(){
  return {
    hasError:true
}
}

頁面首次加載時的性能問題

1.3 memo

shouldComponentUpdate(nextProps,nextState){
  if(nextProps.name === this.props.name){
  //下一次屬性中的name和當(dāng)前屬性中的name,如果相等就不再重新渲染,不想等就重新渲染
    return false
    }else{
        return true
          }
}
//或者用PureCompent,需要導(dǎo)入{PureCompent } from React,只有傳入數(shù)據(jù)的本身對比
//(第一級發(fā)生變化,比如對象內(nèi)部不算)2.傳入回調(diào)函數(shù)每次都會重新渲染),內(nèi)部的數(shù)據(jù)變化就不行
class Foo extends PureCompent{
  
}

memo

//函數(shù)式的不能用Pure,但是有memo
import {memo} from 'react'
const Foo =  memo(function Foo(props){//返回一個組件
  return ()
})

2.React Hooks

類組件的問題:

  • 狀態(tài)難以復(fù)用(渲染組件,高階組件)
  • 渲染屬性和高階組件導(dǎo)致層級冗余
  • 生命周期函數(shù)混雜不相干邏輯
  • 相干邏輯分散在不同的生命周期
  • this指向復(fù)雜
    hooks優(yōu)勢:
  • 函數(shù)組件無this問題
  • 自定義hooks方便復(fù)用狀態(tài)邏輯
  • 副作用關(guān)注點分離

2.1 useState

import {useState} from 'react'
const [count ,setCount] = useState(0)
onClick={()=>{setCount(count +1)}}

use每次渲染按照穩(wěn)定的順序和穩(wěn)定的次數(shù)。

2.2 useEffect

副作用:

  • 綁定事件
  • 網(wǎng)絡(luò)請求
  • 訪問DOM

副作用的時期:

  • Mount之后
  • Update之前
  • Unmount之前
useEffect
useEffect(()=>{
  window.addEventListener('resize',onResize)
  console.log('count')
  return () => {
  //清空狀態(tài)函數(shù)
window.removeEventListener('resize',onResize)
}
},[])

傳入空數(shù)組說明只執(zhí)一次。

2.3 useContext與useMemo/useCallback

import {createContext,useContext} from 'react'
const CountContext = createContext()
<CountContext.Provider value={}></>
function Counter(){
  const count = useContext(CountContext)
console.log(count)
}

useMemo:
僅僅用來做性能優(yōu)化使用,不能做改變渲染邏輯的用途
const double = useMemo(()=>{
return count *3
},[count])調(diào)用時機在渲染期間,而useEffect是在副作用時期,useMemo是有返回值,可以參與渲染,不能循環(huán)依賴
useCallback:

const onClick = useMemo(()=>{
  return ()=>{
  console.log('click')
}
},[])

const onClick = useCallback(()=>{
  console.log('click')
},[])

useMemo返回值是一個函數(shù)。則等價于useCallback
使onclick函數(shù)不會變化,useCallback會創(chuàng)建函數(shù),但是如果沒有變化,則不會返回,當(dāng)依賴變化時,才會執(zhí)行。

2.4 useRef

  • 獲取子組件或者DOM節(jié)點的句柄
  • 渲染周期之間共享數(shù)據(jù)的存儲
    state也能儲存數(shù)據(jù),但state會觸發(fā)重渲染。
import {useRef} from "react"
const counterRef = useRef()
<Counter ref= {counterRef}>
console.log(counterRef.current)
//注意只能是類組件
const it = useRef()
it.current = ....
下一次渲染就能獲取到了

2.5 Redux

redux:狀態(tài)容器與數(shù)據(jù)流管理

  • 單一數(shù)據(jù)源
  • 狀態(tài)不可變(修改完之后不再是以前的Redux)
  • 用純函數(shù)來修改狀態(tài)
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容