jQuery: aspetti del DOM e della performance

jQuery: aspetti del DOM e della performance

jQuery semplifica di molto la gestione del DOM tramite JavaScript. Il DOM è una sigla che sta per Document Object Model, ossia modello a oggetti del documento. Un documento non è necessariamente un documento HTML, ma può essere scritto in qualsiasi linguaggio di marcatura supportato da un browser (XML, SVG, eccetera). Scopo di questo articolo è quello di chiarire alcuni aspetti legati al DOM e a jQuery.

Oggetti jQuery e oggetti DOM

jQuery, tramite il wrapper $(), trasforma un oggetto del DOM in un oggetto jQuery, assegnandogli i metodi e le proprietà della libreria. Si può operare un processo inverso riconvertendo l'oggetto jQuery in un oggetto del DOM. Per esempio, data la seguente marcatura:


<div id="test" class="test"></div>

Quello che segue è un oggetto jQuery:


var test = $('#test');

Possiamo quindi usare i metodi di jQuery:


console.log(test.attr('class')); // 'test'

Ma non quelli del DOM:


console.log(test.className); // Errore!

Per farlo dobbiamo riconvertire l'oggetto in un oggetto del DOM:


var test = $('#test')[0];
console.log(test.className); 'test'

La sintassi è:


var domObject = $(jqueryObject)[0];

Questo passaggio è ancora più evidente nel caso dei metodi di jQuery che operano sugli elementi:


$('#test').click(function() {

	var $test = $(this); // oggetto jQuery
	var test = this;  // oggetto DOM
	
	console.log($test.attr('class')); // 'test'
	console.log(test.className);  // 'test'


});

In questo caso this può operare sia come riferimento ad un oggetto jQuery che ad un oggetto del DOM.

Usare i metodi del DOM con jQuery

Perchè dovremmo usare i metodi del DOM con jQuery se esistono già quelli nativi della libreria? Semplice: i metodi del DOM vengono implementati nativamente nei browser con linguaggi come C++, quindi sono notevolmente più veloci di quelli di jQuery.

Prendiamo ad esempio il metodo getElementById():


var test = document.getElementById('test');
var $test = $('#test');

Apparentemente il risultato è identico, ma se analizziamo il codice della libreria noteremo che jQuery esegue un procedimento di scomposizione dell'espressione CSS passata al wrapper $(). Infatti se il browser supporta le Selectors API, jQuery utilizza quelle, altrimenti il controllo passa all'engine Sizzle per l'elaborazione dell'espressione CSS tramite espressioni regolari.

A questo punto si potrebbe dire: noi vogliamo utilizzare i metodi di jQuery. Come facciamo se utilizziamo il DOM? Semplice: è sufficiente passare l'espressione DOM al wrapper $():


var $test = $(test); // ossia $(document.getElementById('test')

Pensiamo ad esempio al contesto dei selettori. Questa è una soluzione che io uso molto spesso:


var $p = $('p', document.getElementById('test'));

La migliore performance del DOM si rivela con il tipico esempio della proprietà innerHTML (non facente parte delle specifiche ufficiali ma comunque assegnata da tutti i browser a ciascun oggetto di tipo HTMLElement che la accetti).

La controparte jQuery è html(), che però è meno performante della prima. Esempio:


var html = '';
var test = document.getElementById('test');

for(var i = 0; i < 1000; i += 1) {

	html += '<p>' + i + '</p>';


}

test.innerHTML = html;

innerHTML è più veloce perchè i browser utilizzano il loro parser HTML quando usiamo questa proprietà. E dato che in assoluto un parser HTML è forse il componente più veloce di un browser, è chiaro che questa proprietà è da preferire ovunque sia possibile utilizzarla.

Riassumendo: i metodi del DOM sono da preferire se la vostra esigenza primaria è la performance delle vostre pagine. Se avete ad esempio una tabella con 5000 righe, forse sarebbe opportuno valutare le possibilità offerte dal DOM.

Attenzione comunque: alcuni metodi del DOM, come ad esempio quelli relativi alla creazione di elementi e al loro popolamento, possono non essere così efficaci come i metodi di jQuery, soprattutto se pensiamo in termini di verbosità del codice. Esempio:


var test = document.getElementById('test');
var txt = document.createTextNode('Test');
test.appendChild(txt);

In jQuery invece:


$('#test').text('Test');

In questo caso risparmiamo molto codice utilizzando i metodi di jQuery.

Torna su