Как написать метод addDough для моей пиццы с помощью декоратора DP - PullRequest
0 голосов
/ 15 апреля 2019

Я создаю три типа пиццы (куриная, пепперони и вегетарианская), и у каждого из них могут быть дополнительные начинки, которые увеличат цену пиццы (например, дополнительный сыр, колбаса ...), поэтому я знаю, что мне нужно использовать DP-декоратор, но моя проблема в том, что у меня есть 2 вида теста (Flatbread & Thin Crust), и в каждой моей пицце ДОЛЖНО быть тесто, но я не знаю, куда добавить эту часть теста. Вот мой интерфейс Pizza:

public interface Pizza {
    public String getDescription();
    public double getCost();    
 }

Вот мой класс по приготовлению куриной пиццы (пепперони и овощи будут добавлены позже):

public class ChickenPizza implements Pizza {

    @Override
    public String getDescription() {

        return "Chicken";
    }
    @Override
    public double getCost() {

        return 10;
    }
}

Мой класс ToppingDecorator:

public abstract class ToppingDecorator implements Pizza {
    protected Pizza tempPizza;
    public ToppingDecorator(Pizza newPizza) {
        tempPizza=newPizza;
    }

    @Override
    public String getDescription() {
        return tempPizza.getDescription();
    }

    @Override
    public double getCost() {
        return tempPizza.getCost();
    }
}

И мой класс ExtraCheese (колбаса и другие начинки будут добавлены позже):

public class ExtraCheese extends ToppingDecorator{

    public ExtraCheese(Pizza newPizza) {
        super(newPizza);
    }


    public String getDescription() {
        return tempPizza.getDescription()+", Extra Cheese";
    }


    public double getCost() {
        return tempPizza.getCost()+2;
    }
}

Итак, мой вопрос: сначала я подумал, что я должен сделать 2 класса 1 для теста для лепешек, а другой для теста для тонкой корочки (как я сделал для дополнительного сыра), но это не изменит стоимость, затем Я думал, что должен сделать абстрактные методы get и set в интерфейсе Pizza, но я не уверен.

1 Ответ

2 голосов
/ 15 апреля 2019

Существует множество способов реализации шаблона декорирования для украшения объектов дополнительными ингредиентами. Давайте сначала посмотрим на описание, что такое декоратор :

  • Придайте дополнительные обязанности к объекту динамически. Декораторы предоставляют гибкую альтернативу подклассам для расширение функциональности.
  • Указанное клиентом украшение базового объекта рекурсивно оборачивая это.
  • Упаковка подарка, его упаковка в коробку и упаковка в коробку.

Как видите, ограничения выше, и мы обладаем некоторой гибкостью. Мы могли бы думать о пицце как о списке ингредиентов. Мы можем выбрать тесто, овощи и т. Д. Мы можем рассматривать пиццу как ингредиент. Конечно, мы можем создать две иерархии моделей: одну для всех пицц и одну для всех остальных ингредиентов, но одной иерархии должно быть достаточно. Кроме того, для предопределенных ингредиентов мы можем создать новый класс или просто создать гибкий конструктор, который позволяет нам динамически создавать столько ингредиентов, сколько нам нужно. Вы можете легко связать шаблон декоратора с помощью builder или / и abstract factory .

Ниже приведен пример простых декораторов с шаблоном строителя, используемых для приготовления пиццы с заранее определенными ингредиентами и дополнительными пожеланиями:

import java.math.BigDecimal;

public class DesignPatterns {

    public static void main(String[] args) {
        Ingredient chicken = new PizzaBuilder().chicken()
                .withFlatBread()
                .withSausage()
                .build();
        System.out.println(chicken);

        Ingredient pepperoni = new PizzaBuilder().pepperoni()
                .withThinCrust()
                .withSausage()
                .withExtraCheese()
                .build();
        System.out.println(pepperoni);

        Ingredient vegetarian = new PizzaBuilder().vegetarian()
                .withCustomerWish("Mushrooms", BigDecimal.ONE)
                .build();
        System.out.println(vegetarian);
    }
}

class FlatBread extends Ingredient {

    public FlatBread(Ingredient pizza) {
        super(pizza, "Flat bread", new BigDecimal("0.25"));
    }
}

class ThinCrust extends Ingredient {
    public ThinCrust(Ingredient pizza) {
        super(pizza, "Thin Crust", new BigDecimal("0.50"));
    }
}

class ChickenPizza extends Ingredient {

    public ChickenPizza() {
        super("Chicken", new BigDecimal("3.25"));
    }
}

class Pepperoni extends Ingredient {

    public Pepperoni() {
        super("Pepperoni", new BigDecimal("4.50"));
    }
}

class Ingredient {

    private final Ingredient base;
    private final String name;
    private final BigDecimal price;

    public Ingredient(String name, BigDecimal price) {
        this(null, name, price);
    }

    public Ingredient(Ingredient base, String name, BigDecimal price) {
        this.name = name;
        this.price = price;
        this.base = base;
    }

    public String getName() {
        if (base != null) {
            return base.getName() + ", " + name;
        }

        return name;
    }

    public BigDecimal getPrice() {
        if (base != null) {
            return price.add(base.getPrice());
        }

        return price;
    }

    @Override
    public String toString() {
        return '\'' + getName() + "' costs = " + getPrice() + " $";
    }
}

class PizzaBuilder {

    IngredientsBuilder chicken() {
        return new IngredientsBuilder(new ChickenPizza());
    }

    IngredientsBuilder pepperoni() {
        return new IngredientsBuilder(new Pepperoni());
    }

    IngredientsBuilder vegetarian() {
        return new IngredientsBuilder(new Ingredient("Vegetarian", new BigDecimal("2.89")));
    }

    // other pizza types

    class IngredientsBuilder {

        private Ingredient instance;

        private IngredientsBuilder(Ingredient pizza) {
            this.instance = pizza;
        }

        IngredientsBuilder withFlatBread() {
            instance = new FlatBread(instance);
            return this;
        }

        IngredientsBuilder withThinCrust() {
            instance = new ThinCrust(instance);
            return this;
        }

        IngredientsBuilder withSausage() {
            instance = new Ingredient(instance, "Sausage", new BigDecimal("0.49"));
            return this;
        }

        IngredientsBuilder withExtraCheese() {
            instance = new Ingredient(instance, "Extra cheese", new BigDecimal("0.56"));
            return this;
        }

        IngredientsBuilder withCustomerWish(String name, BigDecimal price) {
            instance = new Ingredient(instance, name, price);
            return this;
        }

        // other ingredients

        Ingredient build() {
            return instance;
        }
    }
}

Над отпечатками кодов:

'Chicken, Flat bread, Sausage' costs = 3.99 $
'Pepperoni, Thin Crust, Sausage, Extra cheese' costs = 6.05 $
'Vegetarian, Mushrooms' costs = 3.89 $
...