0

I've been Googling around for a while trying find the answer to this question without any success.

The way I understand how to create a class using the Builder style is like this:

public class MyClass {

    private String myString;
    private int myInt;

      public static class Builder {

        private String myString;
        private int myInt;
  
        public Builder() {}
    
        public Builder setString(String myString) {
          this.myString = myString;
          return this;
        }

        public Builder setInteger(int myInt) {
          this.myInt = myInt;
          return this;
        }

        public MyClass build() {
          return new MyClass(this);
        }

    private MyClass(Builder build) {
      this.myString = build.myString;
      this.myInt = build.myInt;
    }
}

Which is great! It is a powerful style for class design. However, what I would like to do, is have a utility class where everything is static and public but also have a builder to set up the class. But the only way I seem to be able to do that, is by creating a new instance of a builder class which forces the user to call new on the parent class ... but the parent class isn't supposed to be instantiated, so it seems a bit confusing to have a Builder that has to be instantiated for a class that doesn't... The only way I've been able to offer any kind of a builder for a public utility class is by returning void on the final build statement, where all of the build options affect change on the parent class...

So my question is, is there a way to offer "Builder style" functionality on a public static utility class such that there would be no need to instantiate any class at all in the use of that functionality?

Edit:

I guess I should clarify, that what I am trying to offer to an end user of the class, is the ability to invoke a Builder style interface WITHOUT instantiating ANY classes at all... like this:

MyClass.Builder.option1().option2().build();

Notice I did NOT do this:

MyClass myClass = new MyClass.Builder()...

Because that is exactly what I DONT want to do...

Edit2:

Take the following class for example:

import java.util.*;

class MyClass {

    private static List<String>            userList       = new ArrayList<>();
    private static Map<Integer, String>    userMap        = new HashMap<>();
    private static LinkedList<Double>      userDoubleList = new LinkedList<>();
    private static Map<Integer, SomeClass> someClassMap   = new HashMap<>();

    public static void method1(String userString) {
        userList.add(userString);
    }

    public static void method2(Integer userNumber, String userString) {
        userMap.put(userNumber, userString);
    }

    public static void method3(Double userDouble) {
        userDoubleList.addLast(userDouble);
    }

    public static void method4(Integer userInteger, SomeClass userClass) {
        someClassMap.put(userInteger, userClass);
    }
}

I would like for the user to be able to set up the class using a Builder style like this:

MyClass.Builder.option1("My String").option3(25.4).build();

Or however that would end up actually looking ... I want to be able to have them set up the parameters of the class without needing to create a whole bunch of different public static methods that provide the variety of options that are inherent in the class...

I hope that makes sense ...

Michael Sims
  • 2,360
  • 1
  • 16
  • 29
  • Why do you need a builder for a class that does not need to be instantiated? The idea behind having a builder is to create new instances of objects, so no point in having one for a class that has no instances. – akortex Sep 29 '21 at 15:16
  • @AndyTurner When I add public static Builder ... I still have to use the word new in order to use it ... this is what I'm trying to avoid... – Michael Sims Sep 29 '21 at 16:22
  • @akortex - WHY? Because my "telescoping" class constructors are out of control ... and I want to maintain the existing style of using the class which is without instantiation because actually in this case, having to create an instance of the class ruins it's whole purpose for existing ... and I realize that Builders are for creating new classes ... this is why I'm asking the question... – Michael Sims Sep 29 '21 at 16:25
  • @AndyTurner - No, I want to interact with the class without having to use any = at all or the word new ... fully public static class... through and through – Michael Sims Sep 29 '21 at 16:27
  • @AndyTurner - not true ... utility classes don't need to be instantiated to use the methods within them... – Michael Sims Sep 29 '21 at 16:28
  • @AndyTurner - BINGO! And I want to offer a "Builder style" interface for setting up that classes parameters. WITHOUT instantiating ANY classes at all – Michael Sims Sep 29 '21 at 16:31
  • @AndyTurner Look at my edit at the bottom of my post ... I show an example there. – Michael Sims Sep 29 '21 at 16:35
  • "Take the following class for example:" why do you need a builder for a class that only has static state? There's nothing to configure for individual instances. – Andy Turner Sep 29 '21 at 16:50
  • @AndyTurner - Yes I realizE that I can do it that way because that's how I've re-structured my Class ... but I haven't published it yet, because I wanted to find out if there was a way to do what I am trying to do without needing to invoke any classes at all... I know that categorically, what I am asking for seems rather asinine ... or that I'm being picky ... but one of the nicest features of this class is it's existence globally without any instantiation and I wanted to maintain that theme if possible. If not, then so be it ... it is what it is. – Michael Sims Sep 29 '21 at 16:51
  • @AndyTurner - it is when you want to have access to JavaFX Scenes from anywhere in your application... – Michael Sims Sep 29 '21 at 17:05
  • @AndyTurner This is the actual project ... Now keep in mind, I have completely re-written this project literally from a blank screen, implementing builder style ... and it works... you just have to use the word new when you add a scene and I was trying to avoid doing that if at all possible ... which it looks like it's not possible ... but here is the project: https://github.com/EasyG0ing1/Switcher - I haven't published the re-write yet. – Michael Sims Sep 29 '21 at 17:11
  • @AndyTurner - WHY did you delete your answers? – Michael Sims Sep 30 '21 at 12:54

1 Answers1

0

You can use Lombok to produce easily Builders

Use the annotation @Builder on your class

@Builder
public class MyClass {
    private String myString;
    private int myInt;
}

Then you can use it like the following code :

public void foo(){
   MyClass myClass = MyClass.builder().myInt(0).myString("bar").build();
}

Take a look here for lombok

Add the following dependency to manage it

<dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
    <scope>provided</scope>
    <version>1.18.20</version>
</dependency>
J. DEMARE
  • 28
  • 7
  • You don't need lombok for that. Lombok just create the Builder code. And he already has the code. This does not answer his question. – Bentaye Sep 29 '21 at 15:34