Objects, Classes, and Interfaces |
All Java classes have special methods called constructors that are used to initialize a new object of that type. Constructors have the same name as the class--the name of the Rectangle class's constructor isRectangle()
, the name of the Thread class's constructor isThread()
, and so on. Java supports method name overloading so a class can have any number of constructors all of which have the same name. Like other overloaded methods, constructors are differentiated from one another by the number and type of their arguments.Consider the Rectangle class in the java.awt package which provides several different constructors, all named
Rectangle()
, but each with a different number of arguments, or different types of arguments from which the new Rectangle object will get its initial state. Here are the constructor signatures from the java.awt.Rectangle: class:The first Rectangle constructor initializes a new Rectangle to some reasonable default, the second constructor initializes the new Rectangle with the specified width and height, the third constructor initializes the new Rectangle at the specified position and with the specified width and height, and so on.public Rectangle() public Rectangle(int width, int height) public Rectangle(int x, int y, int width, int height) public Rectangle(Dimension size) public Rectangle(Point location) public Rectangle(Point location, Dimension size)Typically, a constructor uses its arguments to initialize the new object's state. So, when creating an object, you should choose the constructor whose arguments best reflect how you want to initialize the new object.
Based on the number and type of the arguments that you pass into the constructor, the compiler can determine which constructor to use. Thus the compiler knows that when you write:
it should use the constructor that requires four integer arguments, and when you write:new Rectangle(0, 0, 100, 200);it should use the constructor that requires one Point object argument and one Dimension object argument.new Rectangle(myPointObj, myDimensionObj);When you are writing your own class, you don't have to provide constructors for it. The default constructor, the constructor that takes no arguments, is automatically provided by the runtime system for all classes. However, often you will want or need to provide constructors for your class.
You declare and implement a constructor just like you would any other method in your class. The name of the constructor must be the same as the name of the class and, if you provide more than one constructor, the arguments to each constructor must differ in number or in type from the others. You do not specify a return value for a constructor.
The constructor for this subclass of Thread, a thread that performs animation, sets up some default values such as the frame speed, the number of images, and loads the images themselves:
Notice how the body of a constructor is just like the body of any other method--it contains local variable declarations, loops, and other statements. However, there is one line in the AnimationThread constructor that you wouldn't see in a regular method--the second line:class AnimationThread extends Thread { int framesPerSecond; int numImages; Image[] images; AnimationThread(int fps, int num) { super("AnimationThread"); this.framesPerSecond = fps; this.numImages = num; this.images = new Image[numImages]; for (int i = 0; i <= numImages; i++) { . . . // Load all the images. . . . } } }This line invokes a constructor provided by the superclass of AnimationThread--Thread. This particular Thread constructor takes a String that sets the name of the Thread. Often a constructor will want to take advantage of initialization code written in a class's upperclass. Indeed, some classes must call their superclass constructor in order for the object to work properly. Typically, the superclass constructor is invoked as the first thing in the subclass's constructor: an object should perform the higher leve initialization first.super("AnimationThread");When declaring constructors for your class, you can use the normal access specifiers to specify what other objects can create instances of your class:
- private
- No other class can instantiate your class as an object. Your class can still contain public class methods, and those methods can construct an object and return it, but no one else can.
- protected
- Only subclasses of your class can create instances of it.
- public
- Anybody can create an instance of your class.
- package-access
- No one outside the package can construct an instance of your class. This is useful if you want to have classes in your package create instances of your class but you don't want to let anyone else.
Objects, Classes, and Interfaces |