如您所知,一个类为对象提供了设计图。您可以从类创建对象。从CreateObjectDemo
程序中获取的以下每个语句都会创建一个对象,并将其分配给变量:
Point originOne = new Point(23, 94);
Rectangle rectOne = new Rectangle(originOne, 100, 200);
Rectangle rectTwo = new Rectangle(50, 100);
第一行创建Point
类的对象, 第二行和第三行分别创建Rectangle
类的对象 。
以上每一个语句中都包含三个部分(下面将详细讨论):
- 声明:以粗体设置的代码是将变量名称与对象类型相关联的所有变量声明。
- 实例化:new关键字是创建对象的Java运算符。
- 初始化:new运算符之后是对构造器的调用,该构造器将初始化新对象。
声明变量以引用对象
先前,您了解到要声明变量,您可以编写:
这将通知编译器您将使用name来引用类型为type的数据。对于基本类型变量,此声明还为该变量保留适当的内存。type name;
您也可以在其行上声明引用变量。例如:
如果这样声明Point originOne;
originOne
,则在实际创建对象并将其分配之前,其值将不确定。仅声明引用变量不会创建对象。为此,您需要使用new
运算符,如下一节所述。您必须先分配一个对象,然后originOne
才能在代码中使用它。否则,您将得到编译器错误。
处于这种状态的变量当前不引用任何对象,可以如下所示(变量名originOne
,加上指向空的引用):
实例化一个类
通过new
创建一个新的对象(实例化一个类)以分配内存,并返回到内存的引用。new
运算符还调用对象的构造器。
注意: 短语“实例化一个类”的含义与“创建对象”相同。创建对象时,将创建类的“实例”,因此将“实例化”一个类。
new
运算符只需要一个后缀参数:一个构造器的调用。构造器的名称提供了要实例化的类的名称。new
运算符返回它创建对象的引用。此引用通常赋值给适当类型的变量,例如:
Point originOne = new Point(23, 94);
由new运算符返回的引用不必分配给变量。也可以直接在表达式中使用。例如:
int height = new Rectangle().height;
初始化对象
这是Point类的代码:
public class Point {
public int x = 0;
public int y = 0;
//constructor
public Point(int a, int b) {
x = a;
y = b;
}
}
此类包含一个构造器。您可以识别构造器,因为其声明使用与类相同的名称,并且没有返回类型。Point类中的构造器采用两个整型参数,如代码(int a,int b)所声明的。以下语句提供23和94作为这些参数的值:
Point originOne = new Point(23, 94);
下图说明了执行此语句的结果:
这是Rectangle类的代码,其中包含四个构造器:
public class Rectangle {
public int width = 0;
public int height = 0;
public Point origin;
// four constructors
public Rectangle() {
origin = new Point(0, 0);
}
public Rectangle(Point p) {
origin = p;
}
public Rectangle(int w, int h) {
origin = new Point(0, 0);
width = w;
height = h;
}
public Rectangle(Point p, int w, int h) {
origin = p;
width = w;
height = h;
}
// a method for moving the rectangle
public void move(int x, int y) {
origin.x = x;
origin.y = y;
}
// a method for computing the area of the rectangle
public int getArea() {
return width * height;
}
}
每个构造器都可以使用基本类型和引用类型为矩形的原点,宽度和高度提供初始值。如果一个类具有多个构造器,则它们必须具有不同的签名。Java编译器根据参数的数量和类型来区分构造器。当Java编译器遇到以下代码时,它知道在Rectangle类中调用构造器,该构造器需要一个Point参数,后跟两个整型参数:
Rectangle rectOne = new Rectangle(originOne, 100, 200);
这将调用Rectangle
的构造器之一将origin
初始化为originOne
。同样,构造器设置width
为100和height
为200。现在有两个对同一个Point对象的引用-一个对象可以对其具有多个引用,如下图所示:
下面的代码调用Rectangle
构造器,该构造器需要两个整型参数,这些参数提供width和height的初始值。如果检查构造器中的代码,您将看到它创建了一个新的Point对象,其x和y值初始化为0:
Rectangle rectTwo = new Rectangle(50, 100);
以下语句中使用的Rectangle构造器不接受任何参数,因此称为无参数构造器:
Rectangle rect = new Rectangle();
所有类都有至少一个构造器。如果一个类没有显式声明任何构造器,则Java编译器会自动提供一个无参数的构造器,称为默认构造器。此默认构造器调用父类的无参数构造器,如果该类没有其他父级,则调用Object
的构造器。如果父级没有构造器(Object
确实有一个构造器),则编译器将拒绝该程序。