简体   繁体   English

使用shouldComponentUpdate优化React Redux组件

[英]Optimizing react redux component with shouldComponentUpdate

This is my first attempt at creating something with react and redux. 这是我用react和redux创建东西的第一次尝试。 So my goal is to build a data table. 所以我的目标是建立一个数据表。 (I probably could have used some existing ones, but I wanted to challange myself with this). (我可能本可以使用一些现有的,但是我想以此来挑战自己)。

The table renders rows only visible on the screen, you can show/hide/swap/pin/resize columns, and every action like this also save profile in localstorage. 该表使行仅在屏幕上可见,您可以显示/隐藏/交换/固定/调整大小列,这样的每个操作也将配置文件保存在本地存储中。 Rows can be filtered, edited and "checked" to do some other actions with them. 可以对行进行过滤,编辑和“检查”,以对行执行其他一些操作。 So the component is pretty comprehensive, with lots of features. 因此,该组件非常全面,具有许多功能。 I have basically done it, and it works. 我基本上已经做到了,而且可行。

But I used redux, and, by following any example online - they say "make one connected component per 'logical' component". 但是我使用了redux,并且通过在网上跟随任何示例,他们说“每个'逻辑'组件组成一个连接的组件”。

So I did it - I have 1 reducer for whole table. 所以我做到了-我整个桌子有1个减速器。 But only now, I noticed a serious lag. 但是直到现在,我注意到严重的滞后。

When I try to type in "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa" in 1 filter input, it hangs up pretty severely. 当我尝试在1个过滤器输入中输入“ aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa”时,它会严重挂断。

The input cell is rather simple - 输入单元格非常简单-

<input ref={el => this.input = el} className="form-control" type="text" value={this.props.value} onChange={this.handleChange} />

And handleChange() dispatches this event to reducer 然后handleChange()将此事件调度到reducer

handleChange(evt) {
    this.props.onFilterInputChange({fieldName: this.props.fieldName, value: this.input.value});
}

And the reducer is a simple one aswell 减速器也是一个简单的

case types.ON_FILTER_INPUT_CHANGE: {
    const spec = {
        currentFilter: {
            [action.params.fieldName]: { $set: action.params.value }
        }
    };
    return update(state, spec);
}

Chrome performace tool records this awful thing as this: Chrome表演工具记录了以下可怕的内容: 在输入“ aaaaaaaaaaaaaaaaaaaaaaaaaaaaa”时,Chrome性能工具

From examples - many said this: 从示例-许多人这样说:

React-redux rerenders only the things that change React-redux只渲染改变的事物

But that was not true. 但这不是事实。 It calls render() for all of the things in the component and that is why my table works so slow. 它为组件中的所有内容调用render(),这就是为什么我的表工作如此缓慢的原因。 I have not added shouldComponentUpdate() to any of my components. 我还没有在我的任何组件中添加shouldComponentUpdate()

My question is: how do I make it work faster? 我的问题是:如何使它运行更快?

Would adding this to all of my components make it better? 将其添加到我的所有组件中会更好吗?

shouldComponentUpdate(newProps, newState) {
    let keys = Object.keys(this.props);
    let result = false;
    for (let i = 0; i < keys.length; i++) {
        if (this.props[keys[i]] !== newProps[keys[i]]) {
            result = true;
            break;
        }
    }
    return result;
}

It seems to make it a bit more responsive. 它似乎使它更具响应性。

But I had doubts about redux before this - storing all of the state in a single atom.. 但是在此之前,我对redux表示怀疑-将所有状态存储在一个原子中。

Its a bit complicated subject but worth the effort. 它的主题有点复杂,但是值得努力。 Some pointers from my earlier answer : 我先前的回答中有一些建议:

apart from this 除此之外

1) Use shouldComponentUpdate/React.PureComponent only if react-perf shows less renders, else your application can give hard-to-debug bugs 1)仅当react-perf显示较少的渲染时,才应使用shouldComponentUpdate / React.PureComponent,否则您的应用程序可能会给出难以调试的错误

2) For components getting more renders(V-DOM renders), use componentWillUpdate to check the cause by diffing old and new props and state. 2)对于获得更多渲染(V-DOM渲染)的组件,请使用componentWillUpdate通过区分新旧道具和状态来检查原因。 Try reducing renders of parent component first and then move toward child, as if parent renders, child will definitely render, no matter whether its props or state changes or not. 尝试先减少父级组件的渲染,然后再移向子级,就像父级渲染一样,子级肯定会渲染,无论其prop或状态是否更改。

3) Use debouncing onchange handler ref 3)使用反跳onchange处理程序ref

4) Although easiets but very good improvement would be noticed, if you can batch your actions by redux-batched-middleware 4)尽管可以轻松实现,但是可以注意到它有很好的改进,如果您可以通过redux-batched-middleware批量执行操作

Remember react always runs its diffing algorithm and produces a new V-DOM on every render, no matter whether physical dom changes or not. 请记住,无论物理dom是否更改,react始终运行其差异算法并在每个渲染上生成新的V-DOM。 You can help reducing these renders with my pointers. 您可以使用指针帮助减少这些渲染。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM