Design patterns are reusable solutions to common software design problems. The Gang of Four (GoF) catalogue defines 23 patterns in three categories: Creational (how objects are created), Structural (how objects are composed), and Behavioral (how objects communicate). Knowing when to apply — and when not to apply — a pattern is a mark of seniority.

Key Points

  • Singleton: one instance per JVM — use enum Singleton for thread-safety without double-checked locking
  • Factory Method: subclasses decide which class to instantiate — decouples creation from use
  • Builder: construct complex objects step by step — avoids telescoping constructors; Lombok @Builder generates it
  • Adapter: wraps incompatible interface — converts one interface to another without modifying source
  • Decorator: adds behaviour dynamically — wraps an object and adds responsibility; Java I/O streams are textbook decorators
  • Proxy: controls access to an object — lazy init, logging, security; Spring AOP and JDK dynamic proxies
  • Observer: one-to-many dependency — when object changes, all dependents notified; EventListener, RxJava, Spring events
  • Strategy: define a family of algorithms, make them interchangeable — eliminates conditionals; Comparator is a strategy
  • Template Method: skeleton algorithm in base class, details in subclasses — Spring's JdbcTemplate, RestTemplate follow this
PatternCategoryJava ExampleProblem solved
SingletonCreationalRuntime.getRuntime()One shared instance
Factory MethodCreationalCalendar.getInstance()Decouple creation
BuilderCreationalStringBuilder, Lombok @BuilderComplex object construction
AdapterStructuralArrays.asList(), InputStreamReaderInterface mismatch
DecoratorStructuralBufferedInputStream(FileInputStream)Add behaviour dynamically
ProxyStructuralSpring @Transactional, Mockito mocksControl access / AOP
ObserverBehavioralEventListener, RxJava, Spring eventsDecouple publisher/subscriber
StrategyBehavioralComparator, Collections.sort()Interchangeable algorithms
Template MethodBehavioralJdbcTemplate, AbstractListSkeleton with pluggable steps

Design patterns in Java: enum Singleton, Builder, Strategy, Spring Observer, I/O Decorator

// Singleton — enum is the safest approach (thread-safe, serialization-safe)
public enum DatabaseConnection {
    INSTANCE;
    private final Connection conn = createConnection();
    public Connection get() { return conn; }
}

// Builder — fluent API
Person person = new Person.Builder("Alice")
    .age(30).email("alice@example.com").city("London").build();

// Strategy — swap algorithms at runtime
interface SortStrategy { void sort(int[] arr); }
class QuickSort implements SortStrategy { ... }
class MergeSort implements SortStrategy { ... }

class Sorter {
    private SortStrategy strategy;
    Sorter(SortStrategy s) { this.strategy = s; }
    void sort(int[] arr) { strategy.sort(arr); }
}

// Observer — Spring application events
@Component class OrderService {
    @Autowired ApplicationEventPublisher publisher;
    void placeOrder(Order o) {
        // ... save order
        publisher.publishEvent(new OrderPlacedEvent(o));
    }
}
@Component class EmailService {
    @EventListener void handle(OrderPlacedEvent e) { sendEmail(e.order()); }
}

// Decorator — I/O streams
InputStream in = new GZIPInputStream(
                     new BufferedInputStream(
                         new FileInputStream("data.gz")));

Real-World Example

Spring Framework is a living catalogue of design patterns: IoC container (Dependency Injection), AOP (Proxy + Decorator), JdbcTemplate (Template Method), ApplicationEvent (Observer), FactoryBean (Factory). Knowing the pattern behind a framework feature helps you configure and debug it correctly.