当上一个道具等于下一个道具时,组件正在更新

Component is updating when previous props are equal to the next props

在简单的待办事项列表应用程序中,我有 FiltersContainer 组件,它为 Filters 组件提供道具:

// FiltersContainer.js
import { connect } from 'react-redux';
import { setVisibilityFilter } from '../actions';
import Filters from '../components/Filters';

function mapStateToProps(state) {
  const { visibilityFilter } = state.todos;

  // `visibilityFilter` variable value is - 'SHOW_ALL'.
  return {
    filters: [{
      title: 'All',
      value: 'SHOW_ALL',
      active: visibilityFilter === 'SHOW_ALL',
    }, {
      title: 'Completed',
      value: 'SHOW_COMPLETED',
      active: visibilityFilter === 'SHOW_COMPLETED',
    }, {
      title: 'Active',
      value: 'SHOW_ACTIVE',
      active: visibilityFilter === 'SHOW_ACTIVE',
    }],
  };
}

function mapDispatchToProps(dispatch) {
  return {
    onFilterClick(value) {
      dispatch(setVisibilityFilter(value));
    },
  };
}

export default connect(mapStateToProps, mapDispatchToProps)(Filters);

问题是,该组件每次状态更改时都会呈现。

例如,切换待办事项会强制呈现 <Filters /> 组件,尽管 filters 数组和visibilityFilter 没有改变。


如果用字符串替换 mapStateToProps 函数中的 filters 数组,则此组件不会在每次状态更改时都呈现:

// FiltersContainer.js
function mapStateToProps(state) {
  const { visibilityFilter } = state.todos;

  return {
    filters: '',
  };
}

完整的应用程序代码可在 - https://github.com/1ven/react-redux-todos

我是不是漏掉了什么?

每次您从 mapStateToProps 返回一个新对象时,这就是旧道具不等于新道具的原因。 因此组件每次都会渲染

如果旧道具不等于新道具,反应渲染组件 在你的情况下你做

 return {
    filters: [{
      title: 'All',
      value: 'SHOW_ALL',
      active: visibilityFilter === 'SHOW_ALL',
    }, {
      title: 'Completed',
      value: 'SHOW_COMPLETED',
      active: visibilityFilter === 'SHOW_COMPLETED',
    }, {
      title: 'Active',
      value: 'SHOW_ACTIVE',
      active: visibilityFilter === 'SHOW_ACTIVE',
    }],
  };

oldProps = 对象

newProps = 另一个对象(虽然内容相同,但都是不同的对象)

oldprops==newprops //没有重新渲染

当你

return {
    filters: '',
  };

oldprops = ''; 新道具 = '' oldprops === newprops 不渲染

问题出在 shallowEqual util 函数中,该函数使用 react-redux 库来检查组件道具是否已更改。

这个函数不做deepEqual检查,只做shallow检查,这就是为什么包含属性和数组的对象不等于同一个对象的原因。