Reaccione el rendimiento: renderizando una lista grande con PureRenderMixin

Tomé un ejemplo de TodoList para reflejar mi problema, pero obviamente mi código del mundo real es más complejo.

Tengo un pseudocódigo como este.

var Todo = React.createClass({
  mixins: [PureRenderMixin], 
  ............ 
}

var TodosContainer = React.createClass({
  mixins: [PureRenderMixin],    

  renderTodo: function(todo) {
     return <Todo key={todo.id} todoData={todo} x={this.props.x} y={this.props.y} .../>;
  },

  render: function() {
     var todos = this.props.todos.map(this.renderTodo)
     return (
          <ReactCSSTransitionGroup transitionName="transition-todo">
                 {todos}
          </ReactCSSTransitionGroup>,
     );
  }

});

Todos mis datos son inmutables, y PureRenderMixin se usa adecuadamente y todo funciona bien. Cuando se modifican los datos de Todo, solo se vuelven a procesar el principal y el todo editado.

El problema es que en algún momento mi lista crece a medida que el usuario se desplaza. Y cuando se actualiza un solo Todo, se necesita más y más tiempo para representar al padre, llameshouldComponentUpdate en todos los todos, y luego renderizar el único todo.

Como puede ver, el componente Todo tiene otro componente que los datos de Todo. Estos son datos que todos los todos requieren para el procesamiento y se comparten (por ejemplo, podríamos imaginar que hay un "displayMode" para todos). Tener muchas propiedades hace que elshouldComponentUpdate realiza un poco más lento.

Además, usandoReactCSSTransitionGroup parece disminuir un poco también, ya queReactCSSTransitionGroup tiene que rendirse yReactCSSTransitionGroupChild incluso antes de lashouldComponentUpdate de todos se llama.React.addons.Perf muestra queReactCSSTransitionGroup > ReactCSSTransitionGroupChild el procesamiento es una pérdida de tiempo para cada elemento de la lista.

Entonces, que yo sepa, yo usoPureRenderMixin pero con una lista más grande esto puede no ser suficiente. Todavía no obtengo resultados tan malos, pero me gustaría saber si hay formas fáciles de optimizar mis representaciones.

¿Alguna idea?

Editar:

Hasta ahora, mi gran lista está paginada, así que en lugar de tener una gran lista de elementos, ahora divido esta gran lista en una lista de páginas. Esto permite tener mejores rendimientos ya que cada página ahora puede implementarshouldComponentUpdate. Ahora, cuando un elemento cambia en una página, React solo tiene que llamar a la función de representación principal que itera en la página, y solo a la función de representación desde una sola página, lo que hace que la iteración funcione mucho menos.

Sin embargo, mi rendimiento de renderización sigue siendo lineal al número de página (O (n)) que tengo. Entonces, si tengo miles de páginas, sigue siendo el mismo problema :) En mi caso de uso, es poco probable que suceda, pero todavía estoy interesado en una mejor solución.

Estoy bastante seguro de que es posible lograr un rendimiento de representación O (log (n)) donde n es el número de elementos (o páginas), dividiendo una lista grande en un árbol (como una estructura de datos persistente) y donde cada nodo tiene el poder de cortocircuitar el cálculo conshouldComponentUpdate

Sí, estoy pensando en algo similar a las estructuras de datos persistentes como Vector en Scala o Clojure:

Sin embargo, estoy preocupado por React porque, hasta donde yo sé, puede tener que crear nodos dom intermedios al representar los nodos internos del árbol. Esto puede ser un problema de acuerdo con el caso de uso (y puede resolverse en futuras versiones de React)

Además, como estamos usando Javascript, me pregunto si Immutable-JS es compatible con esto y hace que los "nodos internos" sean accesibles. Ver:https://github.com/facebook/immutable-js/issues/541

Editar: enlace útil con mis experimentos:¿Puede una aplicación React-Redux realmente escalar tan bien como, por ejemplo, Backbone? Incluso con reselect. En movil

Respuestas a la pregunta(3)

Su respuesta a la pregunta