2017-08-02 3 views
1

Il existe une application qui utilise reaux, redux, react-redux, redux-thunk.react-redux redux-thunk: problème de performance de répartition

react:  "16.0.0-alpha.6" 
redux:  "3.6.0" 
react-redux: "5.0.2" 
redux-thunk: "2.1.0" 

Concept:

: Reducers

import { createStore, applyMiddleware } from 'redux'; 
import thunkMiddleware     from 'redux-thunk'; 

export const MESSAGES_ADD_MESSAGE = 'MESSAGES_ADD_MESSAGE'; 
export const CONTACTS_ADD_CONTACT = 'CONTACTS_ADD_CONTACT'; 

export default function messages(state = { messages: [] }, action) { 
    switch (action.type) { 
     case MESSAGES_ADD_MESSAGE: 
      return { messages: [ ...state.messages, action.message ] }; 
     default: 
      return state; 
    } 
} 

export default function contacts(state = { contacts: [] }, action) { 
    switch (action.type) { 
     case CONTACTS_ADD_CONTACT: 
      return { contacts: [ ...state.contacts, action.contact ] }; 
     default: 
      return state; 
    } 
} 

const rootReducer = combineReducers({ 
    contacts, 
    messages 
}); 

magasin:

const createStoreWithMiddleware = applyMiddleware(
    thunkMiddleware 
)(createStore); 

const store = createStoreWithMiddleware(rootReducer); 

Actions créateurs:

export function addMessage(message) { 
    return { 
     type: MESSAGES_ADD_MESSAGE, 
     message 
    }; 
} 

export function addContact(contact) { 
    return { 
     type: CONTACTS_ADD_CONTACT, 
     contact 
    }; 
} 

Pourquoi l'heure d'envoi (addContact ('Viktor +123456789')) augmente selon le nombre de messages en magasin? Comme je comprends à l'heure de la construction de nouveau magasin, le réducteur de messages renvoie la référence d'état sans créer une nouvelle copie de cette partie du magasin.

J'ai un cas réel plus compliqué mais le concept de problème est similaire.

Répondre

2

Il crée une nouvelle copie à chaque fois que vous modifiez l'état. Si vous voulez améliorer les performances, vous devriez utiliser des bibliothèques comme immutable.js, qui offre de nombreuses optimisations.

De la documentation -

Comme décrit dans Reducers, une fonction réducteur Redux:

doit avoir une signature (previousState, action) => newState, similaire au type de fonction passerait à Array.prototype.reduce (réducteur,? initialValue) Devrait être "pur", ce qui signifie le réducteur: N'effectue pas d'effets secondaires (tels qu'appeler API ou modifier des objets ou variables non-locaux). N'appelle pas fonctions non pures (comme Date.now ou Math.random). Ne mute pas ses arguments . Si le réducteur met à jour l'état, il ne doit pas modifier l'objet d'état existant sur place. Au lieu de cela, il devrait générer un nouvel objet contenant les modifications nécessaires. La même approche doit être utilisée pour tous les sous-objets dans l'état que le réducteur met à jour.

var makeArray = function() 
{ 
    var temp = []; 
    for(let i= 0, i < 10000; i++)  
    temp.push(i); 
    return temp; 
} 

var e = makeArray(); 
var f = makeArray(); 

function test1() 
{ var x = e.push(8); 
} 


var t2 = performance.now(); 

test1(); 

var t3 = performance.now(); 


t3-t2 //0.02 



function test2() 
{ var y = [...f, 8] 
} 


var t2 = performance.now(); 

test2(); 

var t3 = performance.now(); 


t3-t2 //1.98 

Vous pouvez voir test2 est plus lent que test1.

+0

Ok, mais dans ce cas, le cas par défaut de l'opérateur de commutateur dans le réducteur pour quoi? –

+0

Nous ne sommes pas en mutation l'état dans le cas par défaut, il est donc sûr de retourner la référence. – Akhil

+0

Ok, si l'état des messages ne mute pas pendant "dispatch (addContact ('Viktor +123456789'))", pourquoi le temps de cette action augmente selon le nombre de messages en magasin? –