For the basic use of the native useEffect, you can read my article this time to thoroughly understand useEffect, concise and easy to understand.

The native useEffect has several characteristics

  1. UseEffect can be called multiple times.
  2. UseEffect has different execution methods depending on the parameters passed in.

UseEffect steps by hand

Step 1: Use arrays to store different effects

// The previous dependency value
let preArray = [];
// Define the index of effect
let effectId = 0;
Copy the code

Step 2: Determine if the passed parameters are correct

  • An error is reported if the first argument is passed to something other than a function
// An error is reported if the first argument is not a function
if (Object.prototype.toString.call(callback) ! = ='[object Function]') {
    throw new Error('The first argument is not a function')}Copy the code
  • Judge the second parameter
    • ComponentDidMount and componentDidUptate
    • If passed, check whether it is an array or not
    • If it does not, it is the same as the previous dependency value. If it does not, it is the same as the previous dependency value. If not, it is the same as the previous dependency value.
// componentDidMount and componentDidUpdate are equal to componentDidMount and componentDidUpdate
if (typeof array === 'undefined') {
    callback();
} else {
    // Check whether an array is an array
    if (Object.prototype.toString.call(array) ! = ='[object Array]') throw new Error('useEffect's second argument must be an array ')
    // Get the effect of the previous one
    if (preArray[effectId]) {
        // Execute callback if the dependency value is consistent with the previous one
        let hasChange = array.every((item,index) = > item === preArray[effectId][index]) ? false : true;
        if(hasChange) { callback(); }}else {
        callback()
    }
Copy the code

Step 3: Update the dependency values

UseEffect effectId = 0 when the render function is used.

// Update the dependency value
preArray[effectId] = array;
effectId++;
Copy the code

All the code

import React from 'react'
import ReactDOM from 'react-dom'

// Custom Hook
// Customize useState
let states = [];
let setters = [];
let stateid = 0;
function render() {
    stateid = 0;
    effectId = 0;
    ReactDOM.render(<App />.document.querySelector('#root'));
}
function createSetter(stateid) {
    return function (newState) {
        states[stateid] = newState;
        render()
    }
}
function myUseState(initialState) {
    states[stateid] = states[stateid] ? states[stateid] : initialState;
    setters.push(createSetter(stateid));
    let value = states[stateid];
    let setter = setters[stateid];
    stateid++;
    return [value,setter]
}
// The previous dependency value
let preArray = [];
// Define the index of effect
let effectId = 0;
function myUseEffect(callback,array) {
    // An error is reported if the first argument is not a function
    if (Object.prototype.toString.call(callback) ! = ='[object Function]') {
        throw new Error('The first argument is not a function')}// componentDidMount and componentDidUpdate are equal to componentDidMount and componentDidUpdate
    if (typeof array === 'undefined') {
        callback();
    } else {
        // Check whether an array is an array
        if (Object.prototype.toString.call(array) ! = ='[object Array]') throw new Error('useEffect's second argument must be an array ')
        // Get the effect of the previous one
        if (preArray[effectId]) {
            // Execute callback if the dependency value is consistent with the previous one
            let hasChange = array.every((item,index) = > item === preArray[effectId][index]) ? false : true;
            if(hasChange) { callback(); }}else {
            callback()
        }
        // Update the dependency valuepreArray[effectId] = array; effectId++; }}function App() {
    const [count,setCount] = myUseState(0);
    const [name,setName] = myUseState('Joe');
    myUseEffect(() = > {
        console.log('this is the count');
    },[count]);
    myUseEffect(() = > {
        console.log('this is the name');
    },[name]);
    return (
        <div>
            <h1>The current sum is: {count}</h1>
            <button onClick={()= >SetCount (count +1)}> hit me +1</button>
            <h1>Current name: {name}</h1>
            <button onClick={()= >SetName (' li Si ')}> I modify the name</button>
        </div>
    )
}

ReactDOM.render(<App />.document.querySelector('#root'));
Copy the code

Online implementation

  • Handwritten useEffect