Design patterns: Abstract Factory

Mauto 3 min

L’Abstract Factory Pattern è un design pattern creazionale che fornisce un’interfaccia per creare famiglie di oggetti correlati o dipendenti senza specificarne le classi concrete. Questo pattern è utile quando si desidera garantire che un’insieme di oggetti appartenga a una certa famiglia e venga utilizzato in modo coerente.g

Caratteristiche del Abstract Factory pattern

  1. Creazione di famiglie di Oggetti: Permette di creare gruppi di oggetti che appartengono a una certa famiglia o contesto, garantendo che siano compatibili tra loro.
  2. Interfaccia astratta: Fornisce un’interfaccia astratta che definisce i metodi per creare gli oggetti. Le classi concrete implementano questa interfaccia per fornire la logica di creazione specifica.
  3. Indipendenza dalle Classi concrete: L’utente non è a conoscenza delle classi concrete che vengono create. Può utilizzare l’interfaccia dell’abstract factory senza preoccuparsi di come sono implementate le classi concrete.
  4. Facilita l’estensione: Aggiungere nuovi prodotti o famiglie di prodotti diventa più facile. È sufficiente creare una nuova classe che implementa l’interfaccia astratta senza modificare il codice esistente.
  5. Coerenza: Assicura che gli oggetti creati siano coerenti tra loro. Ad esempio, se si crea un’interfaccia utente, si possono generare elementi come bottoni e finestre che appartengono allo stesso tema visivo.
  6. Supporto per la variabilità: Consente di cambiare la famiglia di oggetti creati senza modificare il codice client. Puoi passare a una diversa implementazione dell’abstract factory e ottenere oggetti completamente diversi.

Esempio in PHP:

Immaginiamo di avere due tipi di auto, ognuna delle quali ha due componenti: Sedili e Motore. Possiamo creare due famiglie di auto: Auto di Lusso e Auto Sportiva.

// Interfaccia per i sedili
interface Seats {
    public function createSeats();
}

// Interfaccia per i motori
interface Engine {
    public function createEngine();
}

// Sedili per auto di lusso
class LuxurySeats implements Seats {
    public function createSeats() {
        return "Sedili di lusso";
    }
}

// Sedili per auto sportive
class SportSeats implements Seats {
    public function createSeats() {
        return "Sedili sportivi";
    }
}

// Motore per auto di lusso
class LuxuryEngine implements Engine {
    public function createEngine() {
        return "Motore di lusso";
    }
}

// Motore per auto sportive
class SportEngine implements Engine {
    public function createEngine() {
        return "Motore sportivo";
    }
}

// Abstract Factory
interface CarFactory {
    public function createSeats(): Seats;
    public function createEngine(): Engine;
}

// Factory per auto di lusso
class LuxuryCarFactory implements CarFactory {
    public function createSeats(): Seats {
        return new LuxurySeats();
    }

    public function createEngine(): Engine {
        return new LuxuryEngine();
    }
}

// Factory per auto sportive
class SportCarFactory implements CarFactory {
    public function createSeats(): Seats {
        return new SportSeats();
    }

    public function createEngine(): Engine {
        return new SportEngine();
    }
}

// Utilizzo
function buildCar(CarFactory $factory) {
    $seats = $factory->createSeats();
    $engine = $factory->createEngine();
    
    echo $seats->createSeats() . " con " . $engine->createEngine() . "\n";
}

$factoryLuxury = new LuxuryCarFactory();
$factorySport = new SportCarFactory();

buildCar($factoryLuxury); // Sedili di lusso con Motore di lusso
buildCar($factorySport);  // Sedili sportivi con Motore sportivo

Caso d’uso frequente

Un esempio classico è un’applicazione che gestisce interfacce utente per diversi sistemi operativi (Windows, macOS, Linux). L’abstract factory può fornire metodi per creare componenti come finestre, pulsanti e menu, garantendo che tutti gli oggetti siano progettati per funzionare insieme e rispettare lo stile del sistema operativo specificato.

content_copy Copiato