Incremental Java
Constructors, Part 2

Writing Constructors

Writing a constructor is no different from writing any other method. Well, perhaps a little different. There's no return statement. The purpose of a constructor is to initialize instance variables.

Here's the code for the default (empty) constructor. This would appear in the class

public class Rectangle 
{
  // Instance variables
  int width, height ;

  public Rectangle()
  {
     width = 0 ;
     height = 0 ;
  }

  public Rectangle( int initWidth, int initHeight )
  {
     width = initWidth ;
     height = initHeight ;
  }

  // Other methods omitted for brevity
}
As you can see these methods are not that different from regular methods.

Using "this"

Very often, the parameters of a constructor are used to initialize instance variables. It can be difficult coming up with different parameter names and instance variable names. Why can't the parameter name be width and the instance variable name also be width?
public Rectangle( int width, int height )
{
   width = width ;   //  Doesn't work!
   height = height ; //  Doesn't work!
}
When you see width, is it the parameter variable? Is it the instance variable? You've named them the same!

Interestingly enough, the Java compiler permits this. There's no problem with giving parameter names and instance variable names the same name.

But Java has to pick whether it is an instance variable or a parameter variable. Either way, it doesn't do what you think it should do. It doesn't initialize the instance variables with the values of the parameter variables.

If the compiler has to decide between two variable names, and one is a parameter, and one is an instance variable, it picks the parameter. The instance variable is now shadowed by the parameter variable, and we don't have access.

That is, unless we use this.

public Rectangle( int width, int height )
{
   this.width = width ;   //  Good!
   this.height = height ; //  Good!
}
If you use this. (the word "this" followed by a dot) before a variable, then it assumes that it's an instance variable. So, in this case, this.width is the instance variable while width is the parameter variable.

this is the internal name for the object itself. When you get into the method definition, you don't know what the name of the object is. However, you can refer to this object by this.

this is an object variable, so it holds a handle. It holds a handle to the object that just had this constructor called.

You don't have to declare this. It isn't an instance variable, nor a parameter variable. It's just a way to refer to the object by a generic name.

You can always put this. in front of any instance variable. Some programmers like to do this, because it makes it easy to find the instance variable. Other programmers don't like the extra typing. In that case, they make sure the parameter variable names are always different from the instance variable names.

Special Privileges

When we're in the class definition, we have special privileges. Normally, object users can't access the instance variables directly. They're on the outside. They aren't inside the class definition.

But if you're running code in in the class definition, you can have direct access to the instance variables, even if they are private. (If you couldn't have direct access, then why even bother having instance variables).

In particular, you can refer to something like this.width inside a method definition.

In our previous examples, we only put methods after the dot. In principle, you can put instance variables after the dot, too. However, we make our instance variables private which means object users can't access them directly.

Using predetermined instance variables or parameter names

Some programmers always name instance variables with an underscore at the beginning. Thus, they write _width or _height. This makes it easy to spot instance variables without writing this.. Others hate the way underscores look, especially at the beginning of a variable name.

Some prefer to use standard parameter names in constructors used for initialization. For example, I used initWidth and initHeight. I took the instance variables, and prepended (added at the beginning) the word init, and they became the parameter names.

If I had cost and tax as instance variables, I might have a constructor initCost and initTax as parameter names for a constructor.

You can pick whatever choice you like. It's a matter of personal preference.

Initializing Instance Variables Directly

Unlike C++, Java lets you initialize instance variables with initializers. Here's how it looks: public class Rectangle { // Instance variables with initializers int width = 0, height = 0 ; public Rectangle() { // No need to initialize, since done above } public Rectangle( int initWidth, int initHeight ) { // Need to initialize, here width = initWidth ; height = initHeight ; } // Other methods omitted for brevity } Look at the instance variables. We've initialized them with 0. When a constructor is called, it sets the value of width and height to 0, then jumps into the method body.

We can simplify the default constructor to be empty. However, the second constructor still needs to initialize, because we don't want the values 0 for width and height.

This is one feature of Java (initializing instance variables directly) that many programmers like. Realize this initialization is done just before the method body of any constructor.