Java Builder Template

I recently wrote a builder class and noticed that the standard is as follows

public class PersonBuilder { private String firstName; private String lastName; public PersonBuilder withFirstName(String firstName) { this.firstName = firstName; return this; } public PersonBuilder withLastName(String lastName) { this.lastName = lastName; return this; } public Person build() { return new Person(this); } } 

Is there any drawback, instead, to do the following

 public class PersonBuilder { private Person person; public PersonBuilder withFirstName(String firstName) { person.setFirstName(firstName); return this; } public PersonBuilder withLastName(String lastName) { person.setLastName(lastName); return this; } public Person build() { return person; } } 

I understand that this may be an opinion based question, I was just looking for answers to the question of why it could be a bad or better design.

+6
source share
3 answers

There are several problems with your approach. Some of them are described in previous answers, so I just mentioned the rest.

The biggest problem with your design is that you are using one instance of Person in the builder. This means that if you use the same builder more than once, you will โ€œcreateโ€ the same instance, while clients using it expect two different instances. No need to mention that this can lead to serious chaos in your application.

The answer you received from @Basilevs mentions that setters will be required for a โ€œbuiltโ€ class. This is absolutely true, but I would like to emphasize that this is a huge problem, because it means that the classes you are โ€œbuildingโ€ can never be immutable! In other words, you forbid developers of such classes to use synchronization to ensure thread safety, if necessary, and other mechanisms for solving problems that could have been avoided using a common approach.

+5
source
  • Builder can be used if there are no setters in the constructed class.
  • Taking a constructor as an argument to a constructor leads to a hard link.

The following approach solves these problems:

 public class PersonBuilder { private String firstName; private String lastName; public PersonBuilder withFirstName(String firstName) { this.firstName = firstName; return this; } public PersonBuilder withLastName(String lastName) { this.lastName = lastName; return this; } public Person build() { return new Person(firstName, lastName); } } 
+3
source
 Is there any disadvantage to, instead, doing the following 

Yes, by the time the user calls the withFirstName method, this will lead to NPE , because you have not even created an instance of the person.

+2
source

Source: https://habr.com/ru/post/973916/


All Articles