1

I have a superclass with 3 constructors and I want to know if there is a smarter way to write subclass constructors

public class Person{

private String name;
private int age;
private String homeTown;


public Person(String name){
    this.name = name;
    this.age = 18;
    this.homeTown = "Atlanta";
}

public Person(String name, int age){
    this.name = name;
    this.age = age;
    this.homeTown = "Atlanta";
}

public Person(String name, int age, String homeTown){
    this.name = name;
    this.age = age;
    this.homeTown = homeTown;   
}

I also have a subclass that inherits superclass

public class Student extends Person{
private double avgGPA;
private int ID;
private String[] classes;

public Student(double avgGPA, int ID, String[] classes, String name){
    super(name);
    this.avgGPA = avgGPA;
    this.ID = ID;
    this.classes = classes;
}

public Student(double avgGPA, int ID, String[] classes, String name, int age){
    super(name, age);
    this.avgGPA = avgGPA;
    this.ID = ID;
    this.classes = classes;
}

public Student(double avgGPA, int ID, String[] classes, String name, int age, String homeTown){
    super(name, age, homeTown);
    this.avgGPA = avgGPA;
    this.ID = ID;
    this.classes = classes;
}

My subclass works fine and runs without an error, but I want to know if there is another way to write a constructor for the subclass without writing the same constructor 3 times, just because the super class has 3 different constructors.

3
  • Why not an immutable class, with a private constructor, and 3 static factory methods to take in the parameters? Commented Jun 14, 2017 at 2:48
  • Massively overloaded constructors are an antipattern IMHO; you should consider using a builder pattern instead. Commented Jun 14, 2017 at 2:49
  • im afraid that I am not familiar with the concepts like immutable class. If you can tell me, I will look them up. Commented Jun 14, 2017 at 2:49

3 Answers 3

4

Well, there is something in Java to simplify your superclass. You can invoke another constructor in the same class using this();. So, instead of setting each variable for each constructor, use one variable-setting constructor and use this(); to pass it defaults. For your superclass, you could use these instead:

public Person(String name){
    this(name, 18, "Atlanta");
}

public Person(String name, int age){
    this(name, age, "Atlanta");
}

public Person(String name, int age, String homeTown){
    this.name = name;
    this.age = age;
    this.homeTown = homeTown;   
}

For the subclass, I'd create a private method called setVars which takes in the three variables you'd use: double avgGPA, int ID, and String[] classes. So, instead of setting them in each constructor, your class could look like this:

public Student(double avgGPA, int ID, String[] classes, String name){
    super(name);
    setVars(avgGPA, ID, classes);
}

public Student(double avgGPA, int ID, String[] classes, String name, int age){
    super(name, age);
    setVars(avgGPA, ID, classes);
}

public Student(double avgGPA, int ID, String[] classes, String name, int age, String homeTown){
    super(name, age, homeTown);
    setVars(avgGPA, ID, classes);
}

private void setVars(double avgGPA, int ID, String[] classes) {
    this.avgGPA = avgGPA;
    this.ID = ID;
    this.classes = classes;
}

I think that's about as efficient as you'd get, unless you want to create a static initialization method as QueenSvetlana's answer recommended.

Sign up to request clarification or add additional context in comments.

1 Comment

@programing_is_hard No problem. To address your username: It gets easier. While practice doesn't always make perfect, with programming, it can.
1

Something along the lines of this:

public final class Person{

    private final String name;
    private final int age;
    private final String homeTown;
    private double avgGPA;

    private Person(String name, int age, String homeTown, avgGPA){

        this.name = name;
        this.age = age;
        this.homeTown = homeTown;
        this.avgGPA = avgGPA;
    }

    public static Person createPerson(String name, age, homeTown, avgGPA){
        return new Person(name, age, homeTown, avgGPA);
    }

    public static Person createPersonwithoutHomeTown(String name, age,avgGPA){
        return new Person(name, age, "Atlanta", avgGPA);
    }

    public static Person createPersonwithoutAge(String name,avgGPA){
        return new Person(name, 18, "Atlanta", avgGPA);
    }

}

Immutable objects are objects that don't change their state after creation, and don't allow for sub classing. In the long run, immutable classes are favorable.

3 Comments

Thank you for the answer. My question is, what if avgGPA and other variables on student class is only initialized in Student.java. If I understand your code correctly, it looks like i have to put my avgGPA when I initialize person object.
so If i want to initialize person object without putting avgGPA and at the sametime, make the student code more efficiently, is there any method that I can take?
@programing_is_hard - You can create a static method like in my example above and provide a default GPA, so outside code can't set it (See the createPersonwithoutHomeTown, Client code doesn't provide Atlanta, you do. You even have another method that allows client code to provide home town, if they wanted too). You're the one in control in this case. Remember, my example, is only sample code, read about immutability, static methods and try it
0

I think modifying your Person object to use a builder-pattern would help you.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.