CodeGym /Java Blog /Random-IT /Modello di progettazione di fabbrica
John Squirrels
Livello 41
San Francisco

Modello di progettazione di fabbrica

Pubblicato nel gruppo Random-IT
Ciao amico! Oggi continueremo a studiare i design pattern. In questa lezione parleremo di fabbriche. Discuteremo il problema risolto da questo modello e vedremo un esempio di come una fabbrica può aiutarti ad aprire un bar. Inoltre, ti fornirò 5 semplici passaggi per creare una fabbrica. Modello di progettazione di fabbrica - 1 Per assicurarti che siamo tutti sulla stessa lunghezza d'onda e che capirai rapidamente questo concetto, dovresti avere familiarità con i seguenti argomenti:
  • Ereditarietà in Java
  • Restringimento e ampliamento dei tipi di riferimento in Java
  • Interazione tra diverse classi e oggetti.

Cos'è una fabbrica?

Il modello di progettazione di fabbrica consente di controllare la creazione di oggetti. Il processo di creazione di un nuovo oggetto non è semplicissimo, ma non è nemmeno eccessivamente complicato. Sappiamo tutti che abbiamo bisogno dell'operatore newper creare un nuovo oggetto. Forse sembra che non ci sia nulla da controllare qui, ma non è vero. Supponiamo che la nostra applicazione abbia una certa classe con molti discendenti. Possono sorgere difficoltà quando è necessario creare un'istanza di una classe specifica in base a determinate condizioni. Una fabbrica è un modello di progettazione che aiuta a risolvere il problema della creazione di vari oggetti a seconda di determinate condizioni. Che ne dici di un concetto astratto? Questo diventerà più chiaro e più specifico quando esamineremo l'esempio qui sotto.

Prepariamo vari tipi di caffè

Supponiamo di voler automatizzare una caffetteria. Dobbiamo insegnare al nostro programma come preparare diversi tipi di caffè. Per fare ciò, creeremo una classe di caffè e alcune classi derivate per rappresentare i tipi di caffè che prepareremo: americano, cappuccino, espresso e latte. Iniziamo con una lezione generale sul caffè:

public class Coffee {
    public void grindCoffee(){
        // Grind the coffee
    }
    public void makeCoffee(){
        // Brew the coffee
    }
    public void pourIntoCup(){
        // Pour into a cup
    }
}
Successivamente, creeremo le sue classi figlie:

public class Americano extends Coffee {}
public class Cappuccino extends Coffee {}
public class CaffeLatte extends Coffee {}
public class Espresso extends Coffee {}
I nostri clienti possono ordinare qualsiasi tipo di caffè. I loro ordini devono essere passati al programma. Questo può essere fatto in molti modi, ad esempio usando String. Ma un enumè meglio per questo. Creeremo un enume definiremo i campi enum che corrispondono ai tipi di caffè che possono essere ordinati:

public enum CoffeeType {
    ESPRESSO,
    AMERICANO,
    CAFFE_LATTE,
    CAPPUCCINO
}
Grande. Ora scriviamo il codice per la nostra caffetteria:

public class CoffeeShop {
    
    public Coffee orderCoffee(CoffeeType type) {
        Coffee coffee = null;
        
        switch (type) {
            case AMERICANO:
                coffee = new Americano();
                break;
            case ESPRESSO:
                coffee = new Espresso();
                break;
            case CAPPUCCINO:
                coffee = new Cappucсino();
                break;
            case CAFFE_LATTE:
                coffee = new CaffeLatte();
                break;
        }

        coffee.grindCoffee();
        coffee.makeCoffee();
        coffee.pourIntoCup();

        System.out.println("Here's your coffee! Thanks! Come again!");
        return coffee;
    }
}
Il orderCoffeemetodo può essere suddiviso in due parti:
  1. Creazione di un'istanza specifica di caffè in una switchdichiarazione. Qui è dove una fabbrica fa quello che fa: crea un tipo specifico a seconda delle condizioni.
  2. Preparazione: questa è la macinatura, l'infusione e il versamento in una tazza.
Ecco cosa è importante sapere se è necessario apportare modifiche al metodo in futuro:
  1. I passaggi coinvolti nella preparazione stessa (macinatura, infusione e versamento in una tazza) rimarranno invariati (almeno ci contiamo).
  2. Ma l'assortimento di caffè può cambiare. Forse inizieremo a fare la moka... Frappu... Mochacci... Comunque, un nuovo tipo di caffè.
Possiamo già essere abbastanza fiduciosi che in futuro dovremo apportare modifiche alla switchdichiarazione del metodo. È anche possibile che nella nostra caffetteria il orderCoffeemetodo non sia l'unico luogo in cui creeremo diversi tipi di caffè. Di conseguenza, dovranno essere apportate modifiche in più punti. Probabilmente hai già capito a cosa voglio arrivare. Abbiamo bisogno di refactoring. Sposta il blocco responsabile della creazione del caffè in una classe separata per due motivi:
  1. Possiamo riutilizzare la logica della preparazione del caffè in altri luoghi.
  2. Se l'assortimento cambia, non dovremo modificare il codice ovunque venga creato il caffè. Sarà sufficiente modificare il nostro codice in un solo punto.
In altre parole, è giunto il momento di creare una fabbrica.

Creazione della nostra prima fabbrica

Per fare ciò, creeremo una nuova classe che sarà responsabile solo della creazione delle istanze necessarie delle classi di caffè:

public class SimpleCoffeeFactory {
    public Coffee createCoffee(CoffeeType type) {
        Coffee coffee = null;

        switch (type) {
            case AMERICANO:
                coffee = new Americano();
                break;
            case ESPRESSO:
                coffee = new Espresso();
                break;
            case CAPPUCCINO:
                coffee = new Cappucino();
                break;
            case CAFFE_LATTE:
                coffee = new CaffeLatte();
                break;
        }
        
        return coffee;
    }
}
Congratulazioni! Abbiamo appena implementato il modello di progettazione della fabbrica nella sua forma più semplice (quasi). Sarebbe potuto essere ancora più semplice se avessimo reso il createCoffeemetodo statico. Ma poi perderemmo due capacità:
  1. La capacità di ereditare SimpleCoffeeFactorye sovrascrivere il createCoffeemetodo.
  2. La possibilità di aggiungere l'implementazione di fabbrica richiesta alle nostre classi.
A proposito, parlando di implementazione... Dobbiamo tornare alla caffetteria e aggiungere la nostra fabbrica di caffè.

Aggiunta di una fabbrica alla caffetteria

Riscriviamo la classe del coffee shop usando una factory:

public class CoffeeShop {

    private final SimpleCoffeeFactory coffeeFactory;

    public CoffeeShop(SimpleCoffeeFactory coffeeFactory) {
        this.coffeeFactory = coffeeFactory;
    }

    public Coffee orderCoffee(CoffeeType type) {
        Coffee coffee = coffeeFactory.createCoffee(type);
        coffee.grindCoffee();
        coffee.makeCoffee();
        coffee.pourIntoCup();

        System.out.println("Here's your coffee! Thanks! Come again!");
        return coffee;
    }
}
Eccellente. Ora forniremo una breve descrizione della struttura generale del factory design pattern.

5 passi per aprire la tua fabbrica

Passo 1. Il tuo programma ha una classe con diversi discendenti, come nel diagramma qui sotto: Modello di progettazione di fabbrica - 2Passo 2. Crei un enumcon un campo per ogni classe figlio:

    enum CatType {
        LION,
        TIGER,
        FLUFFY
    }
Passaggio 3. Costruisci la tua fabbrica. Chiamalo CatFactory. Ecco il codice:

class CatFactory {}
Passo 4. Nella tua factory, crea un createCatmetodo che accetti un CatTypeargomento. Ecco il codice:

    class CatFactory {
        public Cat createCat(CatType type) {
            
        }
    }
Passo 5. Nel corpo del metodo, scrivi un'istruzione switchche enumeri i campi enum e crei un'istanza della classe che corrisponde al enumvalore passato:

class CatFactory {
        public Cat createCat(CatType type) {
            Cat cat = null;
            
            switch (type) {
                case LION:
                    cat =  new Fluffy();
                    break;
                case TIGER:
                    cat = new Tiger();
                    break;
                case FLUFFY:
                    cat =  new Lion();
                    break;
            }
            
            return cat;
        }
    }
Ora puoi gestire una fabbrica come un capo. :)

Come esercitarsi

Leggere è buono, scrivere codice è ancora meglio. Se il tuo nome ha un numero pari di lettere, prova a creare la tua pizzeria virtuale. Se il tuo nome ha un numero dispari di lettere, prova a creare un sushi bar virtuale. Se non hai un nome, sei stato fortunato. Oggi puoi rilassarti.
Commenti
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION