react 传递非state给子元素的注意事项

我们是使用react的时候,其实很多情况都不需要使用state去存储值,如果不涉及页面渲染的值,我们往往可以使用 this.xxx的方式;这样可以提高组件的性能,避免不必要的 re_render 带来的消耗
但是如果不稍加注意,可能就会给自己带来很多隐患,甚至bug;
请看如下代码:用非state值向子组件传递一个page属性
export default class Test extends PureComponent {
  constructor(props) {
    super(props);
  //通常我们会把分页的相关信息page为此类的属性,而不是state,因为分页相关的信息,基本不影响渲染,更多的是程序内部的请求使用
this.page = { pageNum: 1, pageSize: 10, }; } handlePageChange = (pagination) => {//分页变化时触发   /***重点***/
Object.assign(
this.page, { pageNum: pagination.current, pageSize: pagination.pageSize, }); }; render() {   return (     <A
      page={this.page}
      handlePageChange={this.handlePageChange}
    />
  );
}
上面代码中的【重点】红色的部分,初学者(像我之前)往往会使用es6的结构赋值语法代替,代码如下:
//如果用以下代码,代替上面的红色部分,最终的结果就会是:    this.page !== A的props.page
this
.page = { ...this.page, pageNum: 1, };

这样的话,会就等于重新创建了一个新的对象,给this.page重新赋值了,

也就是说:我们之前的render中就把this.page对象传递给了子组件,而原来的对象已经与现在的不是同一个了,(现在的是刚刚出炉的新对象),

而且:this.page的改变,与state不同,并不会引起组件的re_render,所以对<A>组件的props的传递并不会再次执行,所以这时候<A>的this.props.page !== <Test>的this.page。他们是两个完全不相干的对象;这时候就会引起BUG

总结如果要传递引用类型给子元素,并且想要保持与父子元素永远指向同一个对象,就不能使用解构赋值,而应该使用: Object.assign( this.page,{ } ); 或者直接 this,page.key = xx;这样就能保证传递给子组件的引用类型,永远是内存中的同一个地址,实现与父组件的同步;

如果传递的是state,则可以无需注意这个,因为当你重新赋值为新对象的时候,程序会执行re_render方法,子组件就会重新获取props,实现与父的实时同步

原文地址:https://www.cnblogs.com/zhilingege/p/8330918.html