DEV Community

Erwan Le Tutour
Erwan Le Tutour

Posted on

Builder design pattern — java

design-pattern

Definition of Builder Pattern

The builder pattern is a design pattern that allows for the step-by-step creation of complex objects using the correct sequence of actions. The construction is controlled by a director object that only needs to know the type of object it is to create.

Where to use the builder pattern?

When you have a simple object, this pattern is not very useful, but when you begin to have a more complex object and want to have a clear code you can use it without hesitation

For example :

package main.builder;
public class Human {
String name;
String lastName;
int age;
public Human(String name, String lastName, int age) {
this.name = name;
this.lastName = lastName;
this.age = age;
}
}
view raw Human.java hosted with ❤ by GitHub

A constructor with a limited number of parameters won’t be something that will make your code unreadable.
But what if now you have something like this :
package main.builder;
import java.util.Date;
public class Human {
String name;
String lastName;
int age;
String height;
String weight;
String eyesColor;
String hairColor;
String birthPlace;
Date birthDate;
int nomberOfSibling;
boolean married;
public Human(String name, String lastName, int age, String height, String weight, String eyesColor, String hairColor, String birthPlace, Date birthDate, int nomberOfSibling, boolean married) {
this.name = name;
this.lastName = lastName;
this.age = age;
this.height = height;
this.weight = weight;
this.eyesColor = eyesColor;
this.hairColor = hairColor;
this.birthPlace = birthPlace;
this.birthDate = birthDate;
this.nomberOfSibling = nomberOfSibling;
this.married = married;
}
}

The number of parameters to pass to the constructor will make the line of code unreadable.
Yes, you can still use the setter to change the value of a property after you have initialized your object. But what if all your fields are final because you want to render them immutable? (What they will be in the rest of this article) Or what if some fields are mandatory and others don’t?

Implementation of the builder pattern

package main.builder;
import lombok.Getter;
import lombok.NoArgsConstructor;
import java.util.Date;
@Getter
public class Human {
private final String name;
private final String lastName;
private final int age;
private final String height;
private final String weight;
private final String eyesColor;
private final String hairColor;
private final String birthPlace;
private final Date birthDate;
private final int numberOfSibling;
private final boolean married;
private Human(HumanBuilder builder){
this.name = builder.name;
this.lastName = builder.lastName;
this.age = builder.age;
this.height = builder.height;
this.weight = builder.weight;
this.eyesColor = builder.eyesColor;
this.hairColor = builder.hairColor;
this.birthPlace = builder.birthPlace;
this.birthDate = builder.birthDate;
this.numberOfSibling = builder.numberOfSibling;
this.married = builder.married;
}
@NoArgsConstructor
public static class HumanBuilder{
private String name;
private String lastName;
private int age;
private String height;
private String weight;
private String eyesColor;
private String hairColor;
private String birthPlace;
private Date birthDate;
private int numberOfSibling;
private boolean married;
public HumanBuilder withName(String name){
this.name = name;
return this;
}
public HumanBuilder withLastName(String lastName){
this.lastName = lastName;
return this;
}
public HumanBuilder withAge(int age){
this.age = age;
return this;
}
public HumanBuilder withHeight(String height){
this.height = height;
return this;
}
public HumanBuilder withWeight(String weight){
this.weight = weight;
return this;
}
public HumanBuilder withEyesColor(String eyesColor){
this.eyesColor = eyesColor;
return this;
}
public HumanBuilder withHairColor(String hairColor){
this.hairColor = hairColor;
return this;
}
public HumanBuilder withBirthPlace(String birthPlace){
this.birthPlace = birthPlace;
return this;
}
public HumanBuilder withBirthDate(Date birthDate){
this.birthDate = birthDate;
return this;
}
public HumanBuilder withNumberOfSibling(int numberOfSibling){
this.numberOfSibling = numberOfSibling;
return this;
}
public HumanBuilder isMarried(boolean married){
this.married = married;
return this;
}
public Human build(){
Human human = new Human(this);
return human;
}
}
@Override
public String toString() {
return "Human{" +
"name='" + name + '\'' +
", lastName='" + lastName + '\'' +
", age=" + age +
", height='" + height + '\'' +
", weight='" + weight + '\'' +
", eyesColor='" + eyesColor + '\'' +
", hairColor='" + hairColor + '\'' +
", birthPlace='" + birthPlace + '\'' +
", birthDate=" + birthDate +
", numberOfSibling=" + numberOfSibling +
", married=" + married +
'}';
}
}

I have used Lombok to not code the getter and the default constructor because the builder pattern doubles the number of lines of code.
So this is the implementation of my HumanBuilder, now how can I declare a Human with it? Nothing difficult you will see (or should I say read ?).
package main.builder;
public class HumanMain {
public static void main(String[] args) {
Human erwan = new Human.HumanBuilder()
.withName("Erwan")
.withAge(30)
.withBirthPlace("Saint Cyr l'Ecole")
.isMarried(true)
.withNumberOfSibling(2)
.build();
System.out.println(erwan.toString());
}
}
view raw HumanMain.java hosted with ❤ by GitHub

That will give this output
Human{
  name='Erwan', 
  lastName='null', 
  age=30, 
  height='null', 
  weight='null', 
  eyesColor='null', 
  hairColor='null', 
  birthPlace='Saint Cyr l'Ecole', 
  birthDate=null, 
  numberOfSibling=2, 
  married=true
}
Enter fullscreen mode Exit fullscreen mode

As you can see, I can choose the number of parameters to initialize and their order.

Speedy emails, satisfied customers

Postmark Image

Are delayed transactional emails costing you user satisfaction? Postmark delivers your emails almost instantly, keeping your customers happy and connected.

Sign up

Top comments (0)

Sentry image

See why 4M developers consider Sentry, “not bad.”

Fixing code doesn’t have to be the worst part of your day. Learn how Sentry can help.

Learn more

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay