Molti sviluppatori sono confusi quando devono scegliere tra un’interfaccia TypeScript o un tipo. Questo probabilmente perché sono molto simili con piccole differenze.

Esploriamo alcune pratiche sensate e predefinite, mentre scopriamo alcune gemme nascoste nel linguaggio TypeScript e rispondiamo alla domanda “Dovrei usare un’interfaccia o un tipo?”

Una volta finito, controlla il mio altro articolo su TypeScript Interfaces vs Classes!

Ecco la mia regola: Per casi d’uso come la creazione di nuovi tipi attraverso cose come primitive, tipi di unione e tipi di tuple, preferisco usare la parola chiave type. Per qualsiasi altra cosa (oggetti/array), è un interface.

Un interface è estremamente utile quando si ha a che fare con strutture di dati in quanto sono una rappresentazione molto visiva (anche se lo è type, questa è tipicamente la mia preferenza). Va benissimo scegliere un type anche per i tuoi oggetti e array.

Nonostante, scopriamo qualcosa di più su Tipi e Interfacce in TypeScript in modo da poter prendere una decisione più informata.

Oggetti: Type vs Interface

In genere definiremmo una struttura dati per modellare un tipo rispetto alle nostre variabili e argomenti di funzione. La maggior parte delle volte una struttura dati è un array o un oggetto che potrebbe contenere alcuni metodi.

Creiamo un oggetto come interfaccia (approccio raccomandato):

interface Milkshake { name: string; price: number; getIngredients(): string;}

Qui preferisco usare un’interfaccia perché è chiaro che è un’interfaccia e non una variabile con dati assegnati – una bella vittoria per la leggibilità. Usiamo name e price per permettere l’impostazione di record e getIngredients come chiamata di metodo.

🎉 Scaricalo gratis!

Pronto ad andare oltre ForEach? Prendi confidenza con i metodi avanzati – Reduce, Find, Filter, Every, Some e Map.

  • Comprendi appieno come gestire le strutture dati JavaScript con operazioni immutabili
  • 31 pagine di sintassi profonda, esempi reali, suggerimenti e trucchi
  • Scrivi una logica di programmazione più pulita e meglio strutturata in 3 ore

✅ Successo! Controlla la tua email, divertiti.

Come bonus extra, ti invieremo anche alcune chicche extra attraverso alcune email extra.

Quando lo confrontiamo con un tipo – potrebbe essere facilmente confuso come un oggetto reale a causa dell’assegnazione =:

type Milkshake = { name: string; price: number; getIngredients(): string;};

Questa è solo la mia piccola preferenza per scegliere un interface invece di usare un type qui – ma sei libero di usare la parola chiave type se vuoi.

Intersezione: Type vs Interface

Intersecare significa semplicemente combinare uno o più tipi! Questo schema può essere realizzato usando sia un interface che un type.

Immaginiamo le seguenti interfacce, vi mostrerò come possiamo intersecare un interface e un type:

interface MilkshakeProps { name: string; price: number;}interface MilkshakeMethods { getIngredients(): string;}

Con un’interfaccia, intersechiamo usando la parola chiave extends. Sto usando più interfacce per mostrarvi come estendere (ereditare) in un’interfaccia finale Milkshake contenente tutte le proprietà e i metodi definiti altrove:

// { name: string, price: number, getIngredients(): string }interface Milkshake extends MilkshakeProps, MilkshakeMethods {}

Ora possiamo usare Milkshake ovunque vogliamo e possiamo beneficiare di avere name, price e getIngredients in un solo riferimento di interfaccia.

Ecco come faremmo lo stesso con un type e intersecando i tipi tramite &:

// { name: string, price: number, getIngredients(): string }type Milkshake = MilkshakeProps & MilkshakeMethods;

Consiglio di usare un type invece di un interface quando volete intersecare dei tipi. Usare extends sembra un po’ più prolisso e non così chiaro da leggere e sento che questo è ciò per cui la parola chiave type è stata fatta.

È anche super facile combinare più tipi con type. Trovo che il codice sia più chiaro che usare extends con le interfacce.

Le interfacce sono anche limitate – l’alias type può essere usato per tipi più complessi come tuple, primitivi, unioni e altro:

// { name: string, price: number, getIngredients(): string }type Milkshake = MilkshakeProps & { getIngredients(): string };

Primitivi: Tipo vs Interfaccia

Parliamo dei tipi primitivi. Sì, stringhe, numeri, ecc. Puoi solo assegnare un tipo primitivo ad un alias type:

type MilkshakeName = string;interface Milkshake { name: MilkshakeName; price: number;}

Se hai bisogno di usare un primitivo, usa un type. Le interfacce sono un no-go qui per un solo valore poiché la sintassi non lo supporta.

🎉 Scaricalo gratis!

Pronto ad andare oltre ForEach? Prendi confidenza con i metodi avanzati – Reduce, Find, Filter, Every, Some e Map.

  • Comprendi appieno come gestire le strutture dati JavaScript con operazioni immutabili
  • 31 pagine di sintassi profonda, esempi reali, suggerimenti e trucchi
  • Scrivi una logica di programmazione più pulita e meglio strutturata in 3 ore

✅ Successo! Controlla la tua email, divertiti.

Come bonus extra, ti invieremo anche alcune chicche extra attraverso alcune email extra.

Per la maggior parte dei casi però, sarebbe più facile usare direttamente il valore primitivo:

interface Milkshake { name: string; price: number;}

Non complicare troppo il tuo codice!

Classi: Tipo vs Interfaccia

Che tu abbia scelto un type o un interface il modo in cui lo usiamo con una classe è lo stesso:

type Size = { size: string};interface Milkshake { name: string; price: number; getIngredients(): string;}class Order implements Size, Milkshake { // Size size = 'large'; // Milkshake name = 'Vanilla'; price = 399; getIngredients() { return ; }}

Le classi non supportano l’implementazione/estensione dei tipi unionali, perché sono considerate come blueprint statici. Questo significa che dovete essere super espliciti su ogni tipo che implementate, poiché non può essere dinamico o cambiare in questo momento a causa delle limitazioni di TypeScript.

Impara di più su TypeScript Interfaces vs Classes!

Functions: Tipo vs Interfaccia

In genere creerei una funzione usando l’alias type poiché la maggior parte delle volte vorremmo digitare una funzione anonima:

type IngredientsFn = () => string;const getIngredients: IngredientsFn = () => ;

Tuttavia, se usare un interface per questo sarebbe più nel tuo stile, ecco come fare:

interface IngredientsFn { () => string;}

Sembra un po’ strano rispetto all’uso di type, ma entrambi sono completamente validi in TypeScript e non c’è differenza quando il codice viene compilato.

Quando non usare un Type

Ora che abbiamo esplorato i vari confronti e approcci raccomandati, è il momento di parlare del Declaration Merging, una caratteristica di TypeScript che si applica solo a interface e sarebbe una ragione per scegliere un interface invece di un type.

Per unire i tipi usando type, dovremmo fare qualcosa del genere e creare un nuovo type finale:

type MilkshakeProps = { name: string; price: number;};type MilkshakeMethods = { getIngredients(): string;};type Milkshake = MilkshakeProps & MilkshakeMethods;

Il nostro type Milkshakeè ora un alias di tipo di MilkshakeProps e MilkshakeMethods. Notate che per ottenere questo comportamento abbiamo dovuto creare Milkshake, dandoci 3 alias di tipo individuali.

Con le interfacce, c’è in effetti un approccio più intelligente (qualcuno potrebbe dire un po’ troppo intelligente) chiamato declaration merging.

Possiamo ottenere un declaration merge semplicemente dichiarando lo stesso interface due volte nello stesso scope (questo potrebbe essere sia importando l’interfaccia da un altro modulo, sia dichiarandola localmente accanto ad un’altra interfaccia):

// declared once...interface Milkshake { name: string; price: number;}// declared again the same, it works!interface Milkshake { getIngredients(): string;}// { name: string, price: number, getIngredients(): string }const milkshake: Milkshake = { name: 'Banana', price: 399, getIngredients() {...}};

Milkshake ora contiene name, price e getIngredients! Tuttavia, la fusione delle dichiarazioni è una buona cosa? Onestamente non sono un fan e sento che potrebbe portare più male che bene. Io comporrei i tuoi tipi attraverso type piuttosto che usare la fusione delle dichiarazioni – ma almeno ora conosci le principali differenze.

Conclusione

Così ci siamo! Le principali differenze tra Tipi e Interfacce in TypeScript.

Per ricapitolare, con anche alcune preferenze personali, io rimarrei con un interface per gli oggetti e userei la parola chiave type alias per comporre nuovi tipi al volo. Questi nuovi tipi potrebbero anche essere da interfacce o altri tipi come tuple, unioni e tipi di intersezione. Ci sono molte possibilità, ma capendo gli approcci possiamo iniziare a scegliere lo strumento giusto.

Per la maggior parte, le interfacce e i tipi sono più o meno gli stessi, a parte qualche differenza coperta qui. Spero che vi sia piaciuto leggere!

Se siete seriamente interessati alle vostre competenze in TypeScript, il vostro prossimo passo è quello di dare un’occhiata ai miei corsi TypeScript, vi insegneranno le basi complete del linguaggio in dettaglio così come molti casi d’uso avanzati di cui avrete bisogno nello sviluppo quotidiano di TypeScript!

Buon coding!

admin

Lascia un commento

Il tuo indirizzo email non sarà pubblicato.

lg