Middle
Čo je to návrhový vzor 'Builder'?
sobes.tech AI
Odpoveď od AI
Vzor "Staviteľ" (Builder) je návrhový vzor určený na krokové vytváranie zložitých objektov. Oddelí proces konštrukcie zložitých objektov od ich reprezentácie, takže rovnaký proces konštrukcie môže vytvárať rôzne reprezentácie.
Princípy fungovania:
- Oddelenie: Oddelí logiku vytvárania objektu od samotného objektu.
- Delegovanie: Klientsý kód (Riaditeľ) deleguje vytváranie objektu na samostatnú triedu (Builder).
- Krokové vytváranie: Objekt je zostavený z komponentov pomocou sady metód staviteľa.
Hlavní účastníci:
- Product: Zložitý objekt, ktorý chceme postaviť. Nezávisí od procesu vytvárania.
- Builder: Abstraktné rozhranie, ktoré definuje kroky na zostavenie Product.
- ConcreteBuilder: Konkrétna implementácia Builder, ktorá realizuje kroky zostavenia a poskytuje metódu na získanie hotového Product.
- Riaditeľ (Voliteľný): Určuje poradie volania krokov zostavenia. Nie je povinný, klientsky kód môže priamo komunikovať s ConcreteBuilder.
Výhody:
- Umožňuje vytváranie objektov s veľkým počtom voliteľných parametrov čitateľnejším spôsobom ako pomocou konštruktorov s množstvom argumentov alebo reťazcov setterov.
- Umožňuje vytváranie rôznych variácií toho istého objektu pomocou rovnakého procesu zostavenia.
- Skrýva vnútornú štruktúru vytváraného objektu.
Nevýhody:
- Môže zvýšiť počet tried v projekte (Builder, ConcreteBuilder, Product, Riaditeľ).
Príklad použitia: Vytvorenie objektu triedy Pizza s rôznymi prísadami.
// Product
public 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 setToppings(List<String> toppings) { this.toppings = toppings; }
@Override
public String toString() {
return "Pizza with dough=" + dough + ", sauce=" + sauce + ", cheese=" + cheese + ", toppings=" + toppings;
}
}
// Builder
public interface PizzaBuilder {
void buildDough();
void buildSauce();
void buildCheese();
void addTopping(String topping);
Pizza getPizza();
}
// ConcreteBuilder
public class MargheritaPizzaBuilder implements PizzaBuilder {
private Pizza pizza;
public MargheritaPizzaBuilder() {
this.pizza = new Pizza();
this.pizza.setToppings(new ArrayList<>()); // Inicializácia zoznamu
}
@Override
public void buildDough() {
pizza.setDough("Thin crust");
}
@Override
public void buildSauce() {
pizza.setSauce("Tomato sauce");
}
@Override
public void buildCheese() {
pizza.setCheese("Mozzarella");
}
@Override
public void addTopping(String topping) {
// Margherita nepridáva toppings okrem základných
}
@Override
public Pizza getPizza() {
return this.pizza;
}
}
// Riaditeľ (Voliteľný)
public class Kitchen {
private PizzaBuilder pizzaBuilder;
public void setPizzaBuilder(PizzaBuilder pb) {
pizzaBuilder = pb;
}
public Pizza getPizza() {
return pizzaBuilder.getPizza();
}
public void constructPizza() {
pizzaBuilder.buildDough();
pizzaBuilder.buildSauce();
pizzaBuilder.buildCheese();
// Môžu byť volané aj iné metódy, napríklad addTopping() v inom builderi
}
}
Použitie:
// Klientsý kód
Kitchen kitchen = new Kitchen();
PizzaBuilder margheritaBuilder = new MargheritaPizzaBuilder();
kitchen.setPizzaBuilder(margheritaBuilder);
kitchenc.constructPizza();
Pizza margherita = kitchen.getPizza();
System.out.println(margherita); // Výstup: Pizza with dough=Thin crust, sauce=Tomato sauce, cheese=Mozzarella, toppings=[]