componentDidMount为何被执行了两次?警告提示componentWillMount已经不推荐使用了。

来源:4-8 React 的生命周期函数

THEEND0123

2022-12-11

import React, { Component, Fragment } from "react";
import TodoItem from "./TodoItem"
// import Test from "./Test";
import "./style.css"

class TodoList extends Component {
    constructor(props){
        super(props);

        this.state = {
            inputValue: "",
            list: []
        }

        this.handleInputChange = this.handleInputChange.bind(this)
        this.handleBtnClick = this.handleBtnClick.bind(this)
        this.handleDelItem = this.handleDelItem.bind(this)

    }

    componentWillMount(){
        console.log("componentWillMount")
    }

    render(){
        console.log("render");
        return (
            <Fragment>
                <div>
                    <label htmlFor="InputArea">输入内容</label>
                    <input
                        id="InputArea" 
                        className="input"
                        value={this.state.inputValue}
                        onChange={this.handleInputChange}
                        ref={(input) => {
                            this.input = input;
                        }}
                    ></input>
                    <button onClick={this.handleBtnClick}>提交</button>
                </div>
                <ul ref={(ul) => {this.ul = ul;}}>
                    {this.getTodoItem()}
                </ul>
            </Fragment>
        )
    }

    componentDidMount(){
        console.log("componentDidMount")
    }

    handleInputChange(e){
        const value = this.input.value;
        this.setState(() => ({inputValue: value}))
    }

    handleBtnClick(){
        this.setState((prevState)=>({
            list:[...prevState.list, prevState.inputValue],
            inputValue:""
        }), () => {
            console.log(this.ul.querySelectorAll('div').length);
        })
    }

    handleDelItem(index){
        this.setState((prevState) => {
            const list = [...prevState.list];
            list.splice(index, 1);

            return {list}
        })
    }

    getTodoItem(){
        return this.state.list.map((item,index) => {
            return <TodoItem 
            key={item}
            content = {item}  
            index = {index} 
            deleteItem = {this.handleDelItem}
            />
        })
    }
}

export default TodoList;

componentDidMount为何被执行了两次?
图片描述

“react”: “18.2.0”,

为啥在index.js去掉React.StrictMode,componentDidMount就被执行了一次。
React.StrictMode是干什么用的?为何有它的时候,componentDidMount被执行了两次。

const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
  // <React.StrictMode>
    <TodoList />
  // </React.StrictMode>
);

警告提示componentWillMount已经不推荐使用了。老师可否介绍一下getDerivedStateFromProps

    static getDerivedStateFromProps(props, state) {
        console.log("componentWillMount")
        return null;
    }
写回答

2回答

Dell

2022-12-17

  1. 严格模式就是会执行两次,目的是校验你的逻辑是否严谨

  2. getDerivedStateFromProps 同学看一下文档,这个我暂时不会补充视频。他这个生命周期函数的意思就是,state 由 props 来生成,当props 发生变化时, state 会跟着发生变化。

1
0

THEEND0123

提问者

2022-12-11

import React, {Component} from "react";
import PropTypes  from  'prop-types';

class TodoItem extends Component{
constructor(props){
super(props);
this.handleClick = this.handleClick.bind(this);
}

render(){
const {test, content} = this.props;
return(
<div onClick={this.handleClick}>
                {test} - {content}
            </div>
)
}

handleClick(){
const {deleteItem,index} = this.props;
deleteItem(index);
}
}

TodoItem.propTypes = {
test: PropTypes.string.isRequired,
content: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
deleteItem: PropTypes.func,
index: PropTypes.number
}

TodoItem.defaultProps = {
test: "hello xxx "
}

export default TodoItem;


0
0

React零基础入门到实战,完成企业级项目简书网站开发

主流新技术 React-redux,React-router4,贯穿基础语法

5275 学习 · 2496 问题

查看课程