Do you want to request a feature or report a bug?
feature
What is the current behavior?
There's very bad performance if I only want to update a very small part of an array with the setState method, which causes the render method is triggered every time I update the array, and the entire array is traversed again and again . As the array gets larger and larger, react takes more resource of the computer, especially CPU. In such cases, calling the DOM method ParentNode.append with the ref feature of react makes a lot better performance than the React's setState way. However, calling the DOM method a lot out of React is not the graceful solution.
I have come across such scenario a few times. Here is an example written in pseudocode.
class DataList extends React.Component {
constructor (props) {
super(props);
this.state = {
dataSourceList = [],
};
}
getData = () => {
// Some data is being fetched from the server
// This piece of data is assigned to a variable, say `newData`
this.setState({
dataSourceList: _.deepClone(this.state.dataSourceList).push(newData)
});
}
render () {
return (
<div>
{
this.state.dataSourceList.map(v => {
return <DataItem key={v.id} value={v.value} />
})
}
</div>
);
}
}
Every time the getData method is invoked, the render method and map method are triggered in order to update the React element array. This does not bother much performance if you fetch these data manually by clicking some button to trigger the getData method.
However, there is a scenario where this costs a lot of CPU resource. I wrote a "streaming log" component with which a line of log was printed to the screen every time the "websocket" receive a message from the server. One piece of message renders the counterpart component DataItem above. Sometimes, the server sends hundreds of thousands of messages within one second, which causes the render method and map method has to be triggered thousands of times accordingly. This behavior even makes the current web page occupy 100% of the CPU and my computer got frozen until the updating process was finished.
In order to solve this issue, I have to use the web API's append method to mount a DOM node carrying those messages directly in to the DOM node of the "steaming log" component' wrapper div. This solution avoids the render part which is under the complexity of O(n) (n is the length of the array). A snippet of pseudocode is as below
class DataList extends React.Component {
getData = () => {
// Some data is being fetched from the server
// This piece of data is assigned to a variable, say `newData`
dataItem = document.createElement('div');
dataItem.innerHTML = newData.value;
this.containerNode.append(dataItem);
}
render () {
return (
<div ref={node => this.containerNode = node} />
);
}
}
Even though using the DOM method append improves the behavior greatly, it is not always the elegant solution. Is it possible that we have a "React" way to update a very small part of the array, or just to pushing an element to the array to be rendered?
If the current behavior is a bug, please provide the steps to reproduce and if possible a minimal demo of the problem. Your bug will get fixed much faster if we can run your code and it doesn't have dependencies other than React. Paste the link to your JSFiddle (https://jsfiddle.net/Luktwrdm/) or CodeSandbox (https://codesandbox.io/s/new) example below:
It is not a bug. It probably be a flaw of the React architecture
What is the expected behavior?
The expected behavior is we may update the array in the above scenario with the original React API rather than directly calling the DOM node's method
Which versions of React, and which browser / OS are affected by this issue? Did this work in previous versions of React?
Present version: v16.x
Browser: All
OS: All
It did not work in previous versions either.
Do you want to request a feature or report a bug?
feature
What is the current behavior?
There's very bad performance if I only want to update a very small part of an array with the
setStatemethod, which causes therendermethod is triggered every time I update the array, and the entire array is traversed again and again . As the array gets larger and larger, react takes more resource of the computer, especially CPU. In such cases, calling the DOM methodParentNode.appendwith thereffeature of react makes a lot better performance than the React'ssetStateway. However, calling the DOM method a lot out of React is not the graceful solution.I have come across such scenario a few times. Here is an example written in pseudocode.
Every time the
getDatamethod is invoked, therendermethod andmapmethod are triggered in order to update the React element array. This does not bother much performance if you fetch these data manually by clicking some button to trigger thegetDatamethod.However, there is a scenario where this costs a lot of CPU resource. I wrote a "streaming log" component with which a line of log was printed to the screen every time the "websocket" receive a message from the server. One piece of message renders the counterpart component
DataItemabove. Sometimes, the server sends hundreds of thousands of messages within one second, which causes therendermethod andmapmethod has to be triggered thousands of times accordingly. This behavior even makes the current web page occupy 100% of the CPU and my computer got frozen until the updating process was finished.In order to solve this issue, I have to use the web API's
appendmethod to mount a DOM node carrying those messages directly in to the DOM node of the "steaming log" component' wrapperdiv. This solution avoids therenderpart which is under the complexity of O(n) (n is the length of the array). A snippet of pseudocode is as belowEven though using the DOM method
appendimproves the behavior greatly, it is not always the elegant solution. Is it possible that we have a "React" way to update a very small part of the array, or just to pushing an element to the array to be rendered?If the current behavior is a bug, please provide the steps to reproduce and if possible a minimal demo of the problem. Your bug will get fixed much faster if we can run your code and it doesn't have dependencies other than React. Paste the link to your JSFiddle (https://jsfiddle.net/Luktwrdm/) or CodeSandbox (https://codesandbox.io/s/new) example below:
It is not a bug. It probably be a flaw of the React architecture
What is the expected behavior?
The expected behavior is we may update the array in the above scenario with the original React API rather than directly calling the DOM node's method
Which versions of React, and which browser / OS are affected by this issue? Did this work in previous versions of React?
Present version: v16.x
Browser: All
OS: All
It did not work in previous versions either.