Sobes.tech
Middle

Co je to builder v kontextu vývoje softwaru?

sobes.tech AI

Odpověď od AI

Vzor návrhu, který odděluje konstrukci složitého objektu od jeho prezentace, umožňuje vytvářet různé prezentace téhož konstrukčního procesu.

Klíčové vlastnosti:

  • Oddělení odpovědností: Logika tvorby objektu (kroky konstrukce) a prezentace objektu (výsledný produkt) jsou oddělené.
  • Krok za krokem konstrukce: Objekt je stavěn krok za krokem, což činí proces flexibilnějším a srozumitelnějším.
  • Různé prezentace: Stejný konstrukční proces může být použit pro tvorbu různých variant objektu.
  • Zapouzdření: Detaily tvorby objektu jsou skryty před klientem, což usnadňuje jeho použití.

Hlavní účastníci:

  • Builder (Stavitel): Abstrétní rozhraní nebo třída, která definuje kroky pro tvorbu částí produktu.
  • ConcreteBuilder (Konkrétní stavitel): Konkrétní implementace stavitele, která skutečně sestavuje části produktu a uchovává výsledek.
  • Director (Ředitel): Třída, která používá objekt ConcreteBuilder k sestavení produktu, voláním odpovídajících metod v určité sekvenci.
  • Product (Produkt): Složitý objekt, který je sestavován.

Příklad použití:

Vytvoření objektu Pizza s různými ingrediencemi:

// Produkt
class Pizza {
    private String dough;
    private String sauce;
    private String cheese;
    private List<String> toppings;

    public void setDough(String dough) { this.dough = dough; }
    public void setSauce(String sauce) { this.sauce = sauce; }
    public void setCheese(String cheese) { this.cheese = cheese; }
    public void addTopping(String topping) {
        if (toppings == null) {
            toppings = new ArrayList<>();
        }
        toppings.add(topping);
    }

    @Override
    public String toString() {
        return "Pizza s těstem: " + dough + ", omáčkou: " + sauce + ", sýrem: " + cheese + ", toppings: " + toppings;
    }
}

// Rozhraní Builder
interface PizzaBuilder {
    void buildDough();
    void buildSauce();
    void buildCheese();
    void addTopping(String topping);
    Pizza getResult();
}

// Konkrétní Builder
class MargheritaPizzaBuilder implements PizzaBuilder {
    private Pizza pizza;

    public MargheritaPizzaBuilder() {
        this.pizza = new Pizza();
    }

    @Override
    public void buildDough() {
        pizza.setDough("Tenčí těsto");
    }

    @Override
    public void buildSauce() {
        pizza.setSauce("Rajčatová omáčka");
    }

    @Override
    public void buildCheese() {
        pizza.setCheese("Mozzarella");
    }

    @Override
    public void addTopping(String topping) {
        // Margherita nemá žádné další toppings ve výchozím nastavení
    }

    @Override
    public Pizza getResult() {
        return pizza;
    }
}

// Ředitel
class Cook {
    private PizzaBuilder pizzaBuilder;

    public void setPizzaBuilder(PizzaBuilder pb) {
        pizzaBuilder = pb;
    }

    public void constructPizza() {
        pizzaBuilder.buildDough();
        pizzaBuilder.buildSauce();
        pizzaBuilder.buildCheese();
        // Další toppings lze přidat zde na základě typu nebo požadavků na pizzu
    }
}

// Klientský kód
public class PizzaShop {
    public static void main(String[] args) {
        Cook cook = new Cook();
        PizzaBuilder margheritaBuilder = new MargheritaPizzaBuilder();

        cook.setPizzaBuilder(margheritaBuilder);
        cook.constructPizza();

        Pizza pizza = margheritaBuilder.getResult();
        System.out.println(pizza);
    }
}

Používá se, když:

  • Je potřeba vytvořit složitý objekt s mnoha volitelnými parametry.
  • Proces tvorby je sekvenční a zahrnuje více kroků.
  • Je třeba vytvořit různé varianty téhož objektu pomocí stejného konstrukčního algoritmu.
  • Je třeba se vyhnout konstruktoru s velkým počtem parametrů ("telescoping constructor").

Výhody:

  • Zlepšuje čitelnost a udržovatelnost kódu.
  • Poskytuje flexibilitu při vytváření objektů.
  • Umožňuje vytváření neměnných (immutable) objektů.
  • Odstraňuje potřebu velkého množství konstruktorů.

Nevýhody:

  • Může zvýšit počet tříd v projektu (pro každý typ objektu a každého stavitele).
  • Vyžaduje počáteční návrhové úsilí.