React:props赋值给state出现的问题

import { render } from 'react-dom'
import React from 'react'

class Child extends React.Component {
  constructor(props) {
    super(props)
    this.state = {
      list: props.list
    }
  }

  handleCilck = () => {
    this.setState({
      list: this.state.list.concat({ name: '小明' })
    })
  }

  render() {
    return (
      <div>
        <button onClick={this.handleCilck}>添加</button>
        {this.state.list.map((item, index) => {
          return <h1 key={index}>Hello, {item.name}</h1>
        })}
        </div>
      )
    }
  }
  
  class Parent extends React.Component {
    constructor(props) {
      super(props)
      this.state = {
        list: [{ name: '小红' }, { name: '小兰' }]
      }
    }
  handleClick = () => {
		this.setState({
		    this.setState({list: [{name: '小绿'}]})
       })
  }
    render() {
      return (
        <div>
       	  <button onClick={this.handleClick}>点击更新props</button>;
          <Child list={this.state.list} />;
        </div>
      )
    }
  }

  export default Parent;

我们想得到的结果是子组件根据父组件传的props值的改变来渲染内容,但是结果显示子组件渲染的列表并不会跟随父组件更新。

子组件会执行render,但是渲染出来的列表数据不变。
**原因:**父组件更新导致子组件更新时,子组件的生命周期执行顺序如下:
在这里插入图片描述
也就是说子组件刷新的时候,不再执行constructor,当然也就不会对state重新赋值,所以子组件虽然执行了render,但是渲染数据不变。

解决方案:
1、在componentWillReceiveProps中重新对state赋值。

componentWillReceiveProps在初始化render的时候不会执行,它会在Component接受到新的状态(Props)时被触发,一般用于父组件状态更新时子组件的重新渲染。
componentWillReceiveProps中想作任何变更最好都将两个状态进行比较,假如状态有异才执行下一步。不然容易造成组件的多次渲染,并且这些渲染都是没有意义的。

componentWillReceiveProps(nextProps) {
	if(nextProps.list !== this.props.list){
		this.setState({
      		list: nextProps.list
   	    })
    } 
}
2、使用getDerivedStateFromProps

这个生命周期函数是为了替代componentWillReceiveProps存在的,所以在你需要使用componentWillReceiveProps的时候,就可以考虑使用getDerivedStateFromProps来进行替代了。

getDerivedStateFromProps是一个静态函数,也就是这个函数不能通过this访问到class的属性,也并不推荐直接访问属性。而是应该通过参数提供的nextProps以及prevState来进行判断,根据新传入的props来映射到state。

需要注意的是,如果props传入的内容不需要影响到你的state,那么就需要返回一个null,这个返回值是必须的,所以尽量将其写到函数的末尾。

static getDerivedStateFromProps(nextProps){
		// 当传入的list 发生变化的时候,更新state
        if(nextProps.list !== this.props.list){
			this.setState({
	      		list: nextProps.list
	   	    })
    	} 
    	// 否则,对于state不进行任何操作
    	return null
   }

参考链接:
https://zhuanlan.zhihu.com/p/83623692
https://juejin.im/post/5cf0e961f265da1b8e7085e6

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值