开发者

nested static builder class, further explanation on its plumbing

开发者 https://www.devze.com 2023-04-05 12:12 出处:网络
public class MyPojo{ String required; Integer optionalOne; Integer optionalTwo; private MyPojo(Builder builder){
public class MyPojo{
    String required;
    Integer optionalOne;
    Integer optionalTwo;

    private MyPojo(Builder builder){
        this.required = builder.required
        this.optionalOne = builder.one;
        this.optionalTwo = builder.two;
    }

    public static class Builder{

        String required;
        Integer optionalOne =0;
        Integer optionalTwo =0;

        public Builder(String req){
            this.required = req;
            return this;
        }
        public Builder optionalOne(Integer one){
            this.one = one;
            return this;
        }
        public Builder optionalTwo(Integer two){
            this.two = two;
            return this;
        }
        public MyPojo build(){
            return new MyPojo(this);
        }
    }
}

Which is then called like this :

MyPojo myPojo = new MyPojo.Builder("req").optionalOne(1).optionalTwo(2).build();

Which is all lovely, but I don't understand a couple of parts.

There are two New statements one in the calling statement and one in the build() method, but there is only one new object created ?

Also, if I then call a second time , without second optional paremeter :

MyPojo myPojo = new MyPojo.Builder("req").o开发者_Python百科ptionalOne(1).build();

Why will optionalTwo revert back to default value (zero). And not keep the value passed in first time(2), its a static class so one instance shared between all MyPojos ?


This bit:

 new MyPojo().Builder("req")

should be:

 new MyPojo.Builder("req")

So you first create a Builder, and then the Build method (which would be better as build btw) creates the immutable object.

If you create a second instance, that's entirely separate from the first. Don't be fooled by the Builder class being declared as static - that just means that an instance of Builder doesn't have an implicit "parent" MyPojo class reference associated with it. The fields of separate Builder instances are still entirely separate.


There are several errors here. As written it does not even compile.

Look up Fluent Interface for how it is supposed to work. Now consider

MyPojo myPojo = new MyPojo.Builder(req).optionalOne(1).optionalTwo(2).Build();

(this is not what you have, this is what you should have)

This is how it works:

  1. new MyPojo.Builder(req) creates a MyPojo.Builder object and assigns the passed req to this.required
  2. .optionOne(1) assigns 1 to MyPojo.Builder.optionalOne. It then returns the same Object (return this). This is the key, because it allows the next step
  3. .optionOne(2) assigns 2 to MyPojo.Builder.optionalTwo to the MyPojo.Builder object returned by the previous call. Note that we are still working with the same Builder object created in step 1. this is returned again
  4. Build() calls Build method on the Builder, which in turn calls the MyPojo constructor. This method should be called build to conform to Java naming conventions.

EDIT: The code is not compilable. EDIT2: Detailed explanation

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号