JAVA 面向对象之深入构造器

版权声明:本文为博主原创文章,未经博主允许可以转载,但请保留原文链接。 https://blog.csdn.net/tmdlife/article/details/52007214

本页面更新日期: 2016年07月23日

前言:

构造器是一个特殊的方法.
这个特殊方法用于创建实例时执行初始化.
构造器是创建对象的重要途径.
因此, java类必需包含一个或一个以上的构造器.

使用构造器执行初始化

构造器的最大的用处就是在创建对象时执行初始化.
前面说过, 当创建一个对象时, 系统为这个对象的实例变量进行默认初始化.
这种默认出的初始化会把所有基本类型的实例变量设为 0(对于数值型实例变量来讲) 或 false (对于布尔型实例变量), 把所有引用类型的实例变量设为 null
如果想改变这种默认的初始化, 想让系统创建对象时就为该对象的实例变量显式指定初始值, 就可以通过构造器来实现.

小提示:
如果程序员没有为 Java类提供任何构造器.
则系统会为这个类提供一个无参数的构造器.
这个构造器的执行体为空,不做任何事情.
无论如何, Java类里至少包含一个构造器.

下面类提供了一个自定义的构造器, 通过这个构造器就可以让程序员进行自定义初始化操作.

public class ConstructorTest
{
  public String name;
  public int count;
  //提供自定义的构造器, 该构造器包含两个参数
  public ConstructorTest(String name, int count)
  {
    //构造器里的 this 代表它进行初始化的对象
    //下面两行代码将传入的 2 个参数赋给 this 所代表对象的 name 和 count 实例变量.
    this.name = name;
    this.count = count;
  }
  public static void main(String[] args)
  {
    //使用自定义的构造器来创建对象
    //系统将会对该对象执行自定义的初始化
    ConstructorTest tc = new ConstructorTest("孙悟空", 108000);
    //输出 ConstructorTest 对象的 name 和 count 两个实例变量
    System.out.println(tc.name);
    System.out.println(tc.count);
  }
}

运行上面的程序, 将看到输出 ConstructorTest 对象时, 它的 name 实例变量不再是 null / count 实例变量不再是 0
这就是提供自定义构造器的作用.

一旦程序员提供了自定义的构造器.
系统就不再提供默认的构造器.
因为上面的 ConstructorTest 类不能再通过 new ConstructorTest(); 代码来创建实例.
因为该类不再包含无参数的构造器.

如果你希望该类保留无参数的构造器, 或者希望有多个初始化过程, 则可以为该类提供多个构造器.
如果一个类里提供了多个构造器, 就形成了构造器的重载.

因为构造器主要用于被其它方法调用, 用以返回该类的实例.
因而通常把构造器设置成 public 访问权限, 从而允许系统中任何位置的类来创建该类的对象.
除非在一些极端的情况下, 业务需要限制创建该类的对象, 可以把构造器设置成其它访问权限, 例如 protected . 主要用于被其子类调用.
把其设置为 private , 就阻止其它类创建该类的实例.

构造器重载

同一个类里具有多个构造器,多个构造器的形参列表不同,即被称为构造器重载.
构造器重载允许Java类里包含多个初始化逻辑,从而允许使用不同的构造器来初始化Java对象.
构造器重载和方法重载基本相似:
要求构造器的名字相同,这一点无须特别要求,因为构造器必需与类名相同.
为了让系统区分不同的构造器,多个构造器的参数列表必需不同.

下面示范构造器的重载,利用构造器重载就可以通过不同的构造器来创建Java对象.

public class ConstructorOverload
{
  public String name;
  public int count;
  //提供无参数构造器
  public ConstructorOverload(){}
  //提供待两个参数的构造器
  public ConstructorOverload(String name, int count)
  {
    this.name = name;
    this.count = count;
  }
  public static void main(String[] args)
  {
    //通过无参数构造器创建 ConstructorOverload 对象
    ConstructorOverload oc1 = new ConstructorOverload();
    //通过有参数构造器创建 ConstructorOverload 对象
    ConstructorOverload oc2 = new ConstructorOverload("孙悟空", 10000);
    //输出看看结果
    System.out.println(oc1.name + " " + oc1.count);
    System.out.println(oc2.name + " " + oc2.count);
  }
}

上面的 ConstructorOverload 类提供了两个重载构造器.
两个构造器的名字相同, 但形参列表不同.
系统通过 new 调用构造器时.
系统将根据传入的实参列表决定调用哪个构造器.

下面来说一种情况:
如果系统包含了多个构造器,例如构造器 A 和 构造器 B
这时, 构造器B包含了构造器A, 如下图所示的包含关系:

这里写图片描述

上图所示就是完全包含这种情况.
如果两个方法之间存在这种关系,则可在方法B中调用方法A.
但构造器不能直接被调用.
构造器必需使用 new 关键字来调用.
但是, 一旦使用 new 关键字来调用构造器, 将会导致系统重新创建一个对象.
为了在构造器B中调用构造器A中的初始化代码, 又不会重新创建一个Java对象.
可以使用this关键字来调用相应的构造器.
下面代码实现了在一个构造器中直接使用另一个构造器的初始化代码.

public class Apple
{
  public String name;
  public String color;
  public double weight;
  public Apple(){}
  //两个参数构造器
  public Apple(String name, String color)
  {
    this.name = name;
    this.color = color;
  }
  //三个参数的构造器
  public Apple(String name, String color, double weight)
  {
    //通过this调用另一个构造器的初始化代码
    this(name, color);
    //下面this引用该构造器正在初始化的Java对象
    this.weight = weight;
  }
}

上面的 Apple 类里包含了三个构造器.
其中第三个构造器通过 this 来调用另一个重载构造器的初始化代码.
程序中 this(name, color); 表明调用该类的另一个带有两个字符串参数的构造器.

使用 this 调用另一个重载构造器这种方法只能在构造器中使用.
而且必需作为构造器执行体的第一条语句.
使用 this 调用重载的构造器时, 系统会根据 this 后面括号里的实参来调用形参列表与之对应的构造器.

猜你喜欢

转载自blog.csdn.net/tmdlife/article/details/52007214