2013-02-19 18 views
5

Ci sono alcune domande che fanno domande sulla memorizzazione nella cache di oggetti jQuery ma non riesco a trovarne una che chieda dove possono e devono essere memorizzati nella cache esattamente gli oggetti jQuery. Ho una pagina web che ha un singolo file JavaScript con un sacco di funzioni come mostrato di seguito.A quale livello dovrei memorizzare nella cache i risultati delle query DOM jQuery?

$(document).ready(function() { 

    // do some setup 
}); 

/* function queries the DOM with the same selector multiple times without caching */ 
function myFunctionOne() { 

    $('#name_input').css("border","1px solid #ccc"); 
    $('#name_input').val(someValue);   
} 

/* function uses cached object from a single query */ 
function myFunctionTwo() { 

    var nameInput = $('#name_input') 
    nameInput.css("border","1px solid #ccc"); 
    nameInput.val(someValue); 
    // do some other stuff with cached selector   
} 

In myFunctionOne I inefficiente interrogare la DOM due volte mentre in myFunctionTwo interrogo DOM volta, memorizzare nella cache il risultato in una variabile locale, quindi lavorare con quella variabile. Comprendo che l'approccio in myFunctionTwo è più efficiente, ma non sono sicuro su dove dovrei effettivamente memorizzare nella cache quegli oggetti. Al momento sto memorizzando l'oggetto nella cache a livello di metodo, ma mi chiedo se posso effettivamente archiviarlo a un livello più alto e poi usarlo su più funzioni. In questo modo, interrogherò il DOM solo una volta e quindi riutilizzerò il risultato in tutte le funzioni di questo file. Un esempio di ciò che sto suggerendo è mostrato di seguito.

$(document).ready(function() { 

    // do some setup 
    var nameInput = $('#name_input') 
}); 

/* function uses cached query result from .ready function above */ 
function myFunctionOne() { 

    nameInput .css("border","1px solid #ccc"); 
    nameInput .val(someValue);   
} 

/* function uses cached query result from .ready function above */ 
function myFunctionTwo() { 

    nameInput.val(someValue); 
    // do some other stuff with cached selector   
} 

Questo approccio è ragionevole o esiste un modo migliore per farlo? Forse usare la funzione .ready è un brutto posto per fare questo tipo di installazione dato che rallenterebbe il caricamento della pagina? Esiste un modo alternativo per memorizzare nella cache gli oggetti jQuery a livello di oggetto o dovrebbero essere solo memorizzati nella cache a livello di funzione?

risposta

7

Come sempre in questo tipo di domande, non ottimizzare prematuramente. In questo caso, significa che non utilizzare alcun caching fino a quando non si noteranno problemi di prestazioni. Se i clienti target utilizzano computer o dispositivi mobili con specifiche insufficienti, ciò significa che si desidera testare personalmente l'hardware a bassa specifica in modo da poter identificare tali problemi. Ti consiglio vivamente di fare chiarezza prima di provare a migliorare la velocità aggiungendo il caching.

Alcuni punti ulteriori:

  • Se si utilizza un selettore che utilizza un ID, dovrebbe essere veloce come userà getElementById dietro le quinte, in modo che non dovrebbe avere bisogno di caching.
  • Utilizzare il metodo di concatenamento invece della memorizzazione nella cache, che utilizzerà il selettore solo una volta
  • Se si implementa la memorizzazione nella cache, farlo prima localmente. La memorizzazione nella cache tra i metodi avrà un costo maggiore nella complessità del codice rispetto alla memorizzazione nella cache locale.
  • L'utilizzo di .ready va bene. Funziona dopo che il DOM è stato caricato ed è il posto giusto per le attività di configurazione.
+1

Concordo con il punto che è importante non ottimizzarlo prematuramente e, nel mio caso, non è prematuro.Sto riscontrando problemi di prestazioni in IE8 e nel tentativo di rettificare questo stiamo osservando alcune delle best practice raccomandate per jQuery, una delle quali è la selezione dei selettori nella cache. Intendo utilizzare il caching locale al minimo e il caching tra i metodi, se possibile. Hai detto, "Il caching tra i metodi avrà un costo maggiore nella complessità del codice rispetto al caching locale". Potete approfondire questo per favore, in quanto ciò potrebbe aiutare a rispondere alla mia domanda iniziale? – user2088756

1

Un approccio potrebbe essere quella di memorizzare il selettore nella $.cache:

$(function(){ 

     var $nameInput = $('#name_input'); 

     $('body').data({ nameInput: $nameInput }); 

}); 

E poi accedervi utilizzando:

function myFunctionOne() { 

    var $nameInput = $('body').data('nameInput'); 
} 
+0

Questo non ha alcun vantaggio rispetto all'utilizzo della propria variabile (evitando un globale se lo si desidera - e dovrebbe essere desiderato - con un wrapper IIFE). Ma ha costi di complessità e prestazioni rispetto all'utilizzo della propria variabile. –

-1

Questo codice si offuscherà in modo soddisfacente. Puoi aggiungere tutti i controlli che desideri in _initControls e utilizzarli in seguito in questo blocco di script. Se lo si desidera globale per tutti i blocchi di script, spostare la funzione _initControls dalla funzione jQuery onreadystate.

$(function() { 
    "use strict"; 

    var _controls = {}, 
    _init = function() { 
     _initControls(); 
     _updateData("Hello"); 
    }, 
    _initControls = function() {    
     _controls.nameInput = $("#name_input"); 
    }, 
    _updateData = function (value) { 
     var nameInput = _controls.nameInput; 
     nameInput.css("border", "1px solid #ccc"); 
     nameInput.val(value); 
    }; 

    _init(); 
}); 
+0

Perché questo post è stato downvoted? – Ankur

Problemi correlati