Why Functional Programming Paradigms Do Not Fully Eliminate the Need for GoF Design Patterns
The software development landscape constantly evolves as developers seek to write more efficient, scalable, and maintainable code. Functional programming (FP) paradigms, with their emphasis on immutability, higher-order functions, and pure comput...

I am Tuanh.net. As of 2024, I have accumulated 8 years of experience in backend programming. I am delighted to connect and share my knowledge with everyone.
1. Understanding Functional Programming and GoF Design Patterns
1.1 What is Functional Programming?
- Immutability: Data cannot be changed after it is created.
- First-Class Functions: Functions can be assigned to variables, passed as arguments, or returned from other functions.
- Pure Functions: Functions produce the same output for the same input without side effects.
// Functional Style: Calculating square of numbers
import java.util.List;
import java.util.stream.Collectors;
public class FunctionalExample {
public static void main(String[] args) {
List<Integer> numbers = List.of(1, 2, 3, 4);
List<Integer> squares = numbers.stream()
.map(n -> n * n)
.collect(Collectors.toList());
System.out.println(squares); // Output: [1, 4, 9, 16]
}
}
1.2 What are GoF Design Patterns?
- Creational Patterns: Singleton, Factory, Builder.
- Structural Patterns: Adapter, Composite, Decorator.
- Behavioral Patterns: Observer, Strategy, Command.
// Singleton Pattern Example
public class Singleton {
private static Singleton instance;
private Singleton() {}
public static Singleton getInstance() {
if (instance == null) {
instance = new Singleton();
}
return instance;
}
}
1.3 Why Compare FP with GoF Patterns?
2. Comparing Functional Paradigms and GoF Design Patterns
2.1 Overlaps Between FP and GoF Patterns
- In OOP, the Strategy pattern enables the selection of algorithms at runtime.
- In FP, the same concept is realized using higher-order functions.
// Functional Strategy Pattern
import java.util.function.BiFunction;
public class StrategyPattern {
public static void main(String[] args) {
BiFunction<Integer, Integer, Integer> add = (a, b) -> a + b;
BiFunction<Integer, Integer, Integer> multiply = (a, b) -> a * b;
int result = executeStrategy(3, 5, add);
System.out.println("Addition Result: " + result);
result = executeStrategy(3, 5, multiply);
System.out.println("Multiplication Result: " + result);
}
private static int executeStrategy(int a, int b, BiFunction<Integer, Integer, Integer> strategy) {
return strategy.apply(a, b);
}
}
- In OOP, decorators enhance the behavior of objects.
- In FP, functions themselves can be composed to achieve similar results.
// Functional Decorator
import java.util.function.Function;
public class FunctionalDecorator {
public static void main(String[] args) {
Function<String, String> addHeader = text -> "Header: " + text;
Function<String, String> addFooter = text -> text + " Footer";
Function<String, String> completeDecorator = addHeader.andThen(addFooter);
String result = completeDecorator.apply("Body content");
System.out.println(result); // Output: Header: Body content Footer
}
}
2.2 Where FP Paradigms Fall Short
- FP lacks built-in constructs to handle complex object creation, a problem addressed by GoF patterns like Builder or Factory.
- Workarounds in FP often involve boilerplate or external libraries.
public class Product {
private String name;
private double price;
private Product(Builder builder) {
this.name = builder.name;
this.price = builder.price;
}
public static class Builder {
private String name;
private double price;
public Builder setName(String name) {
this.name = name;
return this;
}
public Builder setPrice(double price) {
this.price = price;
return this;
}
public Product build() {
return new Product(this);
}
}
}
3. Functional Programming: Complement, Not Replacement
- Use FP for computational logic, transformations, and concurrent processing.
- Use GoF patterns for object creation, structural design, and complex workflows.
4. Conclusion
Read more at : Why Functional Programming Paradigms Do Not Fully Eliminate the Need for GoF Design Patterns





