The life cycle

Different versions of the life cycle site

  1. Mount:

    • constructor
    • componentWillMount()
    • getDerivedStateFromProps(nextProps, prevState): Mount phase has, update phase also has
    • componentDidMount()
  2. Update:

    • componentWillReceiveProps(nextProps)=getDerivedStateFromProps(nextProps, prevState)
    componentWillReceiveProps (nextProps) { nextProps.openNotice ! = =this.props.openNotice&&this.setState({
               openNotice:nextProps. OpenNotice}, () => {console.log(this.state.openNotice:nextProps)
             // Update state to nextProps. The new state can be printed on the second parameter (callback) of setState})}Copy the code
      static getDerivedStateFromProps(nextProps, prevState) {
         if(nextProps.isLogin ! == prevState.isLogin) {return {
             isLogin: nextProps.isLogin,
           };
         }
         return null;
       }
    
       componentDidUpdate(prevProps, prevState) {
         if(! prevState.isLogin &&this.props.isLogin) {
           this.handleClose(); }}Copy the code
    • shouldComponentUpdate(nextProps,nextState)
    • componentWillUpdate(nextProps,nextState)=getSnapshotBeforeUpdate(prevProps, prevState)
    • componentDidUpdate(prevProps,prevState)
  3. Uninstall:

    • componentWillUnMount()

setState



React Render optimized: Diff with shouldComponentUpdate

  • Immutable values
    1. You cannot change the value in this.state directly, and the Render update will not be triggered
  • It may be an asynchronous update
/ / third, setState may be asynchronous update (may be an update) -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --

this.setState({
    count: this.state.count + 1
}, () = > {
    Vue $nexttick-dom
    console.log('count by callback'.this.state.count) // The latest state is available in the callback function
})
console.log('count'.this.state.count) // Async, can not get the latest value
Copy the code
// // setTimeout setState is synchronized
setTimeout(() = > {
    this.setState({
        count: this.state.count + 1
    })
    console.log('count in setTimeout'.this.state.count)
}, 0)
Copy the code
// The setState of the DOM event is synchronized. In componentDidMount
componentDidMount() {
    // The setState of the DOM event is synchronized
    document.body.addEventListener('click'.this.bodyClickHandler)
}

componentWillUnmount() {
    // Destroy custom DOM events in time
    document.body.removeEventListener('click'.this.bodyClickHandler)
    // clearTimeout
}
Copy the code
  • It may be merged
/ / 4, the state asynchronous update, update will be merged before -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
        
        // // incoming objects will be merged (similar to object.assign). The result is +1 only once
        this.setState({
            count: this.state.count + 1
        })
        this.setState({
            count: this.state.count + 1
        })
        this.setState({
            count: this.state.count + 1
        })
Copy the code
// The function passed in will not be merged. +3 this.setState((prevState, props) => {return {count: prevState.count + 1 } }) this.setState((prevState, props) => { return { count: prevState.count + 1 } }) this.setState((prevState, props) => { return { count: prevState.count + 1 } }) }Copy the code
  • Function components have no state by default

  • How does the React component communicate

This in the React component

  1. Why bind this to the React component method
  2. Why bind this to event handlers in the React component

The React event

  • bind this
  • About the Event parameter
  • Pass custom parameters
/ / for the event
clickHandler3 = (event) = > {
    event.preventDefault() // Prevent default behavior
    event.stopPropagation() // Prevent bubbling
    console.log('target', event.target) // Refers to the current element, i.e. the current element is triggered
    console.log('current target', event.currentTarget) // Point to the current element, false!!

    // React encapsulates event. __proto__. Constructor is a SyntheticEvent
    console.log('event', event) // Not a native Event, a native MouseEvent
    console.log('event.__proto__.constructor', event.__proto__.constructor)

    // The native event is as follows. Its __proto__. The constructor is MouseEvent
    console.log('nativeEvent', event.nativeEvent)
    console.log('nativeEvent target', event.nativeEvent.target)  // Refers to the current element, i.e. the current element is triggered
    console.log('nativeEvent current target', event.nativeEvent.currentTarget) // Point to document!!

    // 1. Event is a SyntheticEvent, which simulates all the capabilities of DOM events
    // 2. event.nativeEvent is a nativeEvent object
    // 3. All events are mounted to document
    // 4. Different from DOM events and different from Vue events
}
Copy the code

The React form

  • The controlled components

Values in the component are controlled by this.state:

  1. Input textarea select with value
  2. Use checked the checkbox radio

props

  • Props pass data

  • Props transfer function

  • Props Type Checking

  • What is the nature of JSX

  • What is context? What does it do?

  • shouldComponentUpdate

  • Describes redux monomial data flows

  • SetState is synchronous or asynchronous

Advanced, new

Function component

  • Pure function, input props, output JSX
  • No instance, no life cycle, no state
  • You cannot extend other methods

Uncontrolled component

The value of the component is not controlled by this.state

Usage Scenarios:

  • DOM elements must be manipulated manually, and setState cannot be implemented

  • Documents to go to bed

  • Some rich text editors need to pass in DOM elements

  • Ref:

constructor(props) {
    super(props)
    this.state = {}
    this.nameInputRef = React.createRef() / / create the ref
}
Copy the code
class App extends React.Component {
    constructor(props) {
        super(props)
        this.state = {
            name: The more 'double'.flag: true,}this.nameInputRef = React.createRef() / / create the ref
    }
    render() {
        // input defaultValue
        return <div>{/* use defaultValue instead of value, use ref */}<input defaultValue={this.state.name} ref={this.nameInputRef}/>{/* state does not change with */}<span>state.name: {this.state.name}</span>
            <br/>
            <button onClick={this.alertName}>alert name</button>
        </div>

        // checkbox defaultChecked
        return <div>
            <input
                type="checkbox"
                defaultChecked={this.state.flag}
            />
        </div>

        // file
        return <div>
            <input type="file" ref={this.fileInputRef}/>
            <button onClick={this.alertFile}>alert file</button>
        </div>

    }
    alertName = () = > {
        const elem = this.nameInputRef.current // Get the DOM node from ref
        alert(elem.value) / / not enclosing state. The name
    }
    alertFile = () = > {
        const elem = this.fileInputRef.current // Get the DOM node from ref
        alert(elem.files[0].name)
    }
}
Copy the code
  • DefaultValue, defaulChecked
  • Manipulating DOM elements manually

Portals

Make the component render outside of the parent component

Usage Scenarios:

  • overflow: hidden
  • The z-index value of the parent component is too small
  • Fixed needs to be placed in the first level of body
render() {
    // // Normal rendering
    // return <div className="modal">
    // {this.props.children} {/* vue slot */}
    // </div>

    // Use Portals to render on the body.
    // The fixed element should be placed on the body for better browser compatibility.
    return ReactDOM.createPortal(
        <div className="modal">{this.props.children}</div>.document.body / / the DOM node)}Copy the code

context

Application Scenarios:

  • How is common information (language, topic) passed to each component
  • Too cumbersome to use props
  • Make a mountain out of a molehill with redux

Production data, consumption data (class components and function components are used differently)

import React from 'react'

// Create a Context and fill in the default value (any js variable)
const ThemeContext = React.createContext('light')

// Underlying component - functions are components
function ThemeLink (props) {
    // const theme = this.context // an error is reported. Functional components have no instances, that is, no this

    // Functional components can use Consumer
    return <ThemeContext.Consumer>
        { value => <p>link's theme is {value}</p> }
    </ThemeContext.Consumer>
}

// Underlying component - class component
class ThemedButton extends React.Component {
    // Specify contextType to read the current theme context.
    // static contextType = ThemeContext // ThemedButton.contextType = ThemeContext
    render() {
        const theme = this.context // React will find the nearest theme Provider and use its value.
        return <div>
            <p>button's theme is {theme}</p>
        </div>
    }
}
ThemedButton.contextType = ThemeContext // Specify contextType to read the current theme context.

// Intermediate components no longer have to specify the theme to pass down.
function Toolbar(props) {
    return (
        <div>
            <ThemedButton />
            <ThemeLink />
        </div>)}class App extends React.Component {
    constructor(props) {
        super(props)
        this.state = {
            theme: 'light'}}render() {
        return <ThemeContext.Provider value={this.state.theme}>
            <Toolbar />
            <hr/>
            <button onClick={this.changeTheme}>change theme</button>
        </ThemeContext.Provider>
    }
    changeTheme = () = > {
        this.setState({
            theme: this.state.theme === 'light' ? 'dark' : 'light'}}})export default App
Copy the code

Asynchronous components

  • import()
  • React.lazy
  • React.Suspense
const ContextDemo = React.lazy(() = > import('./ContextDemo'))

<React.Suspense fallback={<div>Loading...</div>} ><ContextDemo/>
</React.Suspense>
Copy the code

Performance optimization

Performance tuning is more important for React

  • shouldComponentUpdate

React Default: The parent component is updated, and the child component is updated unconditionally

  • PureComponent and React. The memo

    1. Shallow comparisons are implemented in PureComponent and React, SCU
    2. Memo, PureComponent of the function component
    3. Shallow comparisons have been used in most cases (try not to make deep comparisons)
  • Immutable value immutable. Js

    1. Embrace immutable values thoroughly
    2. Based on shared data (not deep copy)
const map1 = Immutable.Map({a: 1, b: 2, c: 3})
const map2 = map1.set('b', 50)
map1.get('b') //2
map2.get('b') //50
Copy the code
/ / shouldComponentUpdate increase
shouldComponentUpdate(nextProps, nextState) {
    // _. IsEqual compares the depth of an object or array.
    if (_.isEqual(nextProps.list, this.props.list)) {
        // if it is equal, the rendering is not repeated
        return false
    }
    return true // if not, render
}
Copy the code

React Advanced components

  1. Mixin, deprecated by React
  2. High-level component HOC

Design ideas, one component in, one component out

// Higher-order components
const withMouse = (Component) = > {
    class withMouseComponent extends React.Component {
        constructor(props) {
            super(props)
            this.state = { x: 0.y: 0 }
        }
  
        handleMouseMove = (event) = > {
            this.setState({
                x: event.clientX,
                y: event.clientY
            })
        }
  
        render() {
            return (
                <div style={{ height: '500px'}}onMouseMove={this.handleMouseMove}>{/* 1. Pass through all props 2.<Component {. this.props} mouse={this.state}/>
                </div>)}}return withMouseComponent
}

const App = (props) = > {
    const a = props.a
    const { x, y } = props.mouse // Receive mouse attributes
    return (
        <div style={{ height: '500px' }}>
            <h1>The mouse position is ({x}, {y})</h1>
            <p>{a}</p>
        </div>)}export default withMouse(App) // Return the higher-order function
Copy the code
  1. Render Props

Core idea: Pass the state of a class component as props to a pure function component through a function

class Factory extends React.Component {
	constructor() {
    	this.state = {
        	/*state is the common logical data of multiple components */}}Modified state * / / *
    render(){
    	return <div>{this.props.render(this.state)}</div>}}const App = () = > (
	<Factory render={/ *renderIs a function component */ (props) = > <p>{props.a} {props.b} ..</p>} / >
)
Copy the code

Redux

The basic concept

  • store state
  • action
  • reducer

Reducer (action) reducer -> newState subscribe

Single data flow

react-redux

Asynchronous action

// Synchronize action export const addTodo = text => {return {type: 'ADD_TODO', id: NextTodoId++, text}} // async action export const addTodoAsync = text => { Return (dispatch) => {// Ajax asynchronously fetch data (URL). Then (res => {// execute asynchronous action dispatch(addTodo(res.text))}) }}Copy the code

The middleware

  • redux-thunk
  • redux-promise
  • redux-saga

React-router

Routing mode: Hash, H5 History

  • Hash mode (default), for example, abc.com/#/user/10
  • H5 History mode, such as abc.com/user/20 (se…

Route configuration: Dynamic routing and lazy loading

The React principle

Functional programming

  • A programming paradigm with many concepts

  • Pure functions

  • Immutable values

Vdom and diff

  • H function
  • Vnode data structure
  • The patch function
  1. Compare only the same level, not across levels
  2. If the tag is not the same, it will be deleted and reconstructed without depth comparison
  3. If the tag and key are the same, they are considered the same node and are not compared in depth
{
	tag: 'div',
    props: {
    	className: 'container',
        id: 'div1'
    }
    children: [
    	{tag: 'p', children: 'vdom'},
        {tag: 'ul', props: { style: 'font-size: 20px'}, children: [{tag: 'li', children: 'a'}]},
    ]
}
Copy the code

JSX nature

  • React.createElement, the h function, returnsvnode
  • The first parameter could be a component or an HTML tag
  • Component name must be capitalized (Rect rules)

Synthetic events

  • All events are mounted to document
  • Events are not native, but syntheticEvents synthesize event objects
  • Unlike Vue events, and unlike DOM events

Function:

  1. Better compatibility and cross-platform
  2. Mount to document to reduce memory consumption and avoid frequent untying
  3. Facilitate unified management of events (e.g. transaction mechanisms)

setState batchUpdate

  • Sometimes asynchronous (common use), sometimes synchronous (setTimeout, custom DOM event: addEventListener)
  • Sometimes merge (Object form), sometimes not merge (function form)

SetState main process

BatchUpdate mechanism

  1. SetState doesn’t matter whether it’s asynchronous or synchronous
  2. See if the batchUpdate mechanism can be hit
  3. Judge isBatchingUpdates

Hit batchUpdate mechanism:

  1. The lifecycle (and the functions it calls)
  2. Events registered in React (and functions it calls)
  3. React can manage the entry

Failed to hit batchUpdate mechanism:

  1. SetTimeout setInterval etc. (and the function it calls)
  2. Custom DOM events (and the functions it calls)

Transaction mechanism

Component rendering process

  • props state
  • Generate vnode render ()
  • patch(elem,vnode)

How does JSX render to pages

  • JSX is the createElement function
  • Execute vNode generation
  • Patch (elem, vnode) and patch (vnode, newVnode)

How do I update the page after setState

  • SetState (newState) –> dirtyComponents(may have child components)
  • Generate newVnode render ()
  • patch(vnode,newVnode)

fiber

Patch is divided into two phases:

  • Reconciliation phase – Performs diff algorithm, pure JS calculation
  • Commit stage – Render the DIff results into the DOM

Existing performance problems

  • JS is single-threaded and shares a thread with DOM rendering
  • When a component is complex enough, the calculation and rendering of component updates are stressful
  • At the same time, there are DOM manipulation requirements (animation, mouse drag and drop, etc.), will be stalled

Solution fiber

React internal operating mechanism

  • Split tasks in the Reconciliation phase (COMMIT cannot split)
  • DOM needs to be paused when rendering and resumed when idle
  • window.requestIdleCallback

The interview questions

How do components communicate with each other

  • Parent and child component props
  • Custom events
  • The story and the Context

JSX nature

  • createElement
  • Execute to return to vNode

What is Context? How do you apply it?

  • A parent component that passes information to all its descendants
  • Such as some simple public information: theme color, language, etc
  • Complex public information, using Redux

ShouldComponentUpdate purposes

  • Performance optimization
  • Use this parameter together with immutable values. Otherwise, errors may occur

Redux single data stream

SetState scenario questions

What is a pure function

  • Returns a new value, with no side effects and no changes to the original value
  • Important: immutable values
  • arr1 = arr.slice()

React component life cycle

  • Single component life cycle
  • Parent component life cycle
  • Pay attention to the SCU

React initiates Ajax in which lifecycle

  • componentDidMount

Render list, why use key

  • Key must be used, and cannot be index or random
  • In the DIff algorithm, the tag and key are used to determine whether it is a sanmeNode
  • Reduce rendering times and improve rendering performance

A function component is different from a class component

  • Pure function, input props, output JSX
  • No instance, no life cycle, no state
  • You cannot extend other methods

What is a controlled component

  • The value of the form, controlled by state
  • You need to listen on onChange, update state
  • Contrast uncontrolled components

When to use asynchronous components

  • Loading large components
  • Route lazy loading

Multiple components have common logic. How do I separate them

  • High order component
  • Render Props
  • The mixin has been deprecated by React

How does Redux make asynchronous requests

  • Use asynchronous Action
  • As the story – thunk

How to configure lazy loading on the react-router

What’s the difference between PureComponent

  • ShouldComponentUpdate implements shallow comparisons
  • Optimize performance
  • But use it in conjunction with immutable values

React events and DOM events

  • All events are mounted to document
  • Events are not native, but syntheticEvents synthesize event objects
  • dispatchEvent

React Performance Optimization

  • Add key to render list
  • Custom events and DOM events are destroyed in time
  • Use asynchronous components wisely
  • Reduce the number of times you bind this
  • Use SCU PureComponent and Memo wisely
  • Use Immutable. Js wisely
  • Optimization at the Wepack level
  • Common front-end performance optimizations, such as lazy image loading
  • Using SSR

React vs. Vue

  • Both support componentization
  • It’s all data-driven views
  • Both use VDOM to manipulate dom
  • React uses JSX to embrace JS and Vue uses templates to embrace HTML
  • React functional programming, Vue declarative programming
  • React is more self-reliant, Vue gives you what you want

Good article

  1. In-depth analysis: How to implement a Virtual DOM algorithm