开发者

Java Constructor Overloading using multiple methods

I have a program assignment in class. I already understand the basics of overloading but I am thoroughly confused on one point. How do I output from only the method I am trying to use? Well let me show you the code than explain.

public class Box {
 private int length, width, height;

 public Box(int length){
  this.length=length;
  System.out.println("Line created with length of" + length + ".");
 }
 public Box(int length, int width){
  this.length = length;
  this.width = width;
  System.out.println("Rectangle created with the length of " + length + " ");
  System.out.println("and the width of " + width + ".");
 }
 public Box(int length, int width, int height){
  this.length=length;
  this.width=width;
  this.height=height;
  System.out.println("Box created with the length of " + length + ", ");
  System.out.println("the width of " + width + ", ");
  System.out.println("and the height of " + height +".");

 }
}


class BoxTest {

 public static void main(String[] args) {
  Box BoxObject1 = new Box(1,0,0);
  Box BoxObject2 = new Box(1,2,0);
  Box BoxObject3 = new Box(1,2,3);



 }

}

Ok Now then! How do I call in the class BoxTest to output only what is given. For instance using Box BoxObject1 I want to output "Line created with lenght of XX" not the rest. For Box Box Object2 I want to ouput "Rectangle created with length of XX and width of XX". I am not sure what to add开发者_开发知识库 next for this to happen. Any help would be greatly appreciated.


I guess

  Box BoxObject1 = new Box(1,0,0);
  Box BoxObject2 = new Box(1,2,0);
  Box BoxObject3 = new Box(1,2,3);

is meant to be

  Box BoxObject1 = new Box(1);
  Box BoxObject2 = new Box(1,2);
  Box BoxObject3 = new Box(1,2,3);

At the moment, all three of your calls are calling the third constuctor (passing 0 for some of the arguments).


Box BoxObject1 = new Box(1,0,0);
Box BoxObject2 = new Box(1,2,0);
Box BoxObject3 = new Box(1,2,3);

These are all calling the 3-argument constructor. Perhaps you actually wanted:

Box BoxObject1 = new Box(1);
Box BoxObject2 = new Box(1,2);
Box BoxObject3 = new Box(1,2,3);


so you want this:

Box BoxObject1 = new Box(1);
Box BoxObject2 = new Box(1,2);
Box BoxObject3 = new Box(1,2,3);


To invoke a constructor similar to the way you will invoke a method you use the signature of the constructor. That is: Name, Number and Type of parameters.

So to call the first constructor with a single int parameter then you call:

        new Box(1);

which will invoke the constructor with signature public Box(int length).


You may also consider constructing your class like so that constructors can leverage each other reducing the amount of code duplication:

public class Box {

    private int length, width, height;

    public Box(int length) {
        this.length = length;
        System.out.println("Line created with length of " + length + ".");
    }

    public Box(int length, int width) {
        this(length);
        this.width = width;
        System.out.println("and the width of " + width + ".");
    }

    public Box(int length, int width, int height) {
        this(length, width);
        this.height = height;
        System.out.println("and the height of " + height + ".");
    }

}

Although not appropriate for this use case (as per the reasons given by extraneon) the following is an alternate possibility, useful if you have a variable number of parameters.

public class Box {

    private int length, width, height;

    public Box(int... param) {
        if(param.length > 0) {
            length = param[0];
            System.out.println("Line created with length of " + length + ".");
        }
        if(param.length > 1) {
            width = param[1];
            System.out.println("and the width of " + width + ".");
        }
        if(param.length > 2) {
            height = param[2];
            System.out.println("and the height of " + height + ".");
        }
    }

}

Both of these approaches work with the following:

public class Demo {

    public static void main(String[] args) {
        //new Box(1);
        new Box(1,2);
        //new Box(1,2,3);
    }
}

To give you the desired output:

Line created with length of 1.
and the width of 2.


What you are doing is similar to constructor telescoping. This doesn't scale well and has the same disadvantages listed in the link provided. A constructor should be able to create an object that satisfies all the invariants. For the step-wise build of an Object use a Builder.


As a comment on your question, and not really an answer:

if you have constructors which share part of the setup (as yours do) you can call other constructors from within a constructor:

public class Box {
 private int length, width, height;

 public Box(int length){
  this.length=length;
  System.out.println("Line created with length of" + length + ".");
 }
 public Box(int length, int width){
  this(length); // calls Box(length)
  this.width = width;
  System.out.println("and the width of " + width + ".");
 }
 public Box(int length, int width, int height){
  this(length, width); // calls Box(length, width) which calls Box(length)
  this.height=height;
  System.out.println("and the height of " + height +".");    
 }
}    

In this case the constructors are quite trivial but if you have constructors which contain somewhat more code it will help you prevent code duplication and thus bugfixing (and possibly forgetting to fix one of the constructors). It also highlights the differences between the constructors.

Also consider Pangea's advice on using a builder. It's more readable:

// if no parameters are required and all are optional
Box box0 = new Box.Builder().build();
Box box1 = new Box.Builder().length(1).build();
Box box2 = new Box.Builder().length(1).width(2).build();
Box box3 = new Box.Builder().length(1).width(2).height(3).build();

// if length is required and others are optional - that's your Box
Box box1 = new Box.Builder(1).build();
Box box2 = new Box.Builder(1).width(2).build();
Box box3 = new Box.Builder(1).width(2).height(3).build();

// For comparison - your constructors. It's less obvious what is length, 
// width or height
Box box1 = new Box(1);
Box box2 = new Box(1,2);
Box box3 = new Box(1,2,3);


You should think about something like this. It's a lot cleaner. One constructor is the "general purpose constructor." Were you to change the internal implementation details, you would change this one constructor.

This solution has the virtue of eliminating a lot of duplicate code.

public class Box
{
    private int length, width, height;

    public Box(int length)
    {
        this(length, 0, 0);
    }
    public Box(int length, int width)
    {
        this(length, width, 0);
    }
    public Box(int length, int width, int height){
    this.length=length;
    this.width=width;
    this.height=height;
    System.out.println("Box created with the length of " + length + ", ");
    System.out.println("the width of " + width + ", ");
    System.out.println("and the height of " + height +".");
    }
    public static void main(String[] args)
    {
        Box BoxObject1 = new Box(1);
        Box BoxObject2 = new Box(1,2);
        Box BoxObject3 = new Box(1,2,3);
    }
}

Here is the result at the command line.

morrison@odonata:~$ java Box
Box created with the length of 1, 
the width of 0, 
and the height of 0.
Box created with the length of 1, 
the width of 2, 
and the height of 0.
Box created with the length of 1, 
the width of 2, 
and the height of 3.
morrison@odonata:~$ 
0

上一篇:

下一篇:

精彩评论

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

最新问答

问答排行榜