3 modi per definire una classe in JavaScript

E' importante puntualizzare che non esistono classi in Javascript. Le funzioni possono essere utilizzare per simulare una classe, ma in generale Javascript risulta essere un linguaggio senza classi.
3 modi per definire una classe in JavaScript

Specifiche sulla traduzione

Di seguito la traduzione dell’articolo “3 ways to define a JavaScript class” di Stoyan Stefanov.

JavaScript è un linguaggio orientato agli oggetti molto flessibile quando si tratta di sintassi. In questo articolo troverai 3 modi per definire e istanziare oggetti. Anche se ne hai già uno preferito, ti insegneremo qualche alternativa al fine di leggere e capire codice scritto da altre persone.

E’ importante puntualizzare che non esistono classi in Javascript. Le funzioni possono essere utilizzare per simulare una classe, ma in generale Javascript risulta essere un linguaggio senza classi. Qualsiasi cosa è un oggetto. Quando si parla di ereditarietà, sono gli oggetti che ereditano da altri oggetti, non classi da altre classi come nei “class-ici” linguaggi.

1. Usare una funzione

Questa è probabilmente una delle opzioni più comuni. Si definisce una normalissima funzione e si usa la keyword new per creare un oggetto. Per definire le proprietà e i metodi associati all’oggetto creato con function(), puoi usare la keyword this, come nel seguente esempio:


function Apple (type) {
    this.type = type;
    this.color = "red";
    this.getInfo = getAppleInfo;
}

// Questo è un anti-pattern! Continua a leggere...
function getAppleInfo() {
    return this.color + ' ' + this.type + ' apple';
}

Per istanziare un oggetto utilizza il costruttore funzione Apple, imposta le proprietà e chiama i metodi come qui di seguito:

var apple = new Apple('macintosh');
apple.color = "reddish";
alert(apple.getInfo());

1.1. Metodi definiti internamente

Nell’esempio precedente si evince che il metodo getInfo() relativo alla “classe” Apple è stato definito in una funzione getAppleInfo() a parte. Anche se questo funziona bene, ha uno svantaggio – definiendole tutte seguendo questa metodologia saranno tutte nel “namespace globale”. Questa cosa può creare conflitti a livello di naming se tu ad esempio (o qualche altra libreria che stai usando) istanzia un’altra funzione con lo stesso nome. Il modo per prevenire questo tipo di problematiche è di definire i tuoi metodi all’interno della funzione costruttore:

function Apple (type) {
    this.type = type;
    this.color = "red";
    this.getInfo = function() {
        return this.color + ' ' + this.type + ' apple';
    };
}

Utilizzando questa sintassi non modificherà il modo in cui si crea l’istanza dell’oggetto e l’utilizzo delle sue proprietà e metodi.

1.2. Aggiungere metodi al prototipo

Un inconveniente del passaggio 1.1 risiede nel fatto che il metodo getInfo() è ricreato ogni volta che si crea un nuovo oggetto. A volte potrebbe essere quello il comportamento voluto, ma è di solito raro che ciò sia voluto. Un modo più economico e snello è quello di aggiungere getInfo() al prototipo della funzione costruttore.

function Apple (type) {
    this.type = type;
    this.color = "red";
}
 
Apple.prototype.getInfo = function() {
    return this.color + ' ' + this.type + ' apple';
};

A questo punto potrai usare il nuovo oggetto alla stessa maniera dei precedenti casi 1 e 1.1

2. Oggetti di tipo literal

I literals rappresentano un metodo short per definire oggetti e array. Per creare un oggetto vuoto puoi farlo cosi:

var o = {};

// instead of the "normal" way:
var o = new Object();

//For arrays you can do:
var a = [];

//instead of:
var a = new Array();

In questo modo potrai saltare la sintassi class-like e creare un istanza immediatamente. Abbiamo le stesse funzionalità descritte negli esempi precedenti ma usando la sintassi literal:

var apple = {
    type: "macintosh",
    color: "red",
    getInfo: function () {
        return this.color + ' ' + this.type + ' apple';
    }
}

In questo caso tu non hai bisogno (e non puoi) creare un’istanza della classe perché essa esiste già. Devi semplicemente cominciare ad usarla.

apple.color = "reddish";
alert(apple.getInfo());

Tale oggetto è anche talvolta chiamato singleton. Nei linguaggi classici come java, singleton significa che è possibile avere una sola istanza di questa classe in qualsiasi momento e non puoi creare più oggetti dalla stessa classe. In javascript, che non ha classi, questo concetto non ha più alcun senso in quanto tutti gli oggetti sono singleton dal principio.

3. Singleton e le funzioni

Il terzo metodo presentato in questo articolo è una combinazione dei precedenti due. Tu puoi usare una funzione per definire un oggetto singleton. Questa è la sintassi:

var apple = new function() {
    this.type = "macintosh";
    this.color = "red";
    this.getInfo = function () {
        return this.color + ' ' + this.type + ' apple';
    };
}

Come puoi notare, è molto simile alla versione 1.1, ma la modalità di utilizzo ricalca in pieno la numero 2.

apple.color = "reddish";
alert(apple.getInfo());

new function(){…} fa due cose allo stesso tempo_ definisce una funzione e la invoca con new. Potrebbe sembrare un po confuso se non siete abituati ad esso e infatti non è molto comune, ma è una opzione, quando si vuole veramente una funzione di tipo costruttore che verrà utilizzata solo una volta e non ha quindi molto senso darle un nome.

Conclusioni

Hai visto tre (più uno) modi di creare oggetti in JavaScript. Ricordate che (nonostante il titolo dell’articolo) non esiste una cosa come una classe in JavaScript.

Search
Tags
Seleziona rubrica
Seleziona rubrica
Codice Github