第二章 类与对象的基本概念

一、面向对象的程序设计方法概述

面向对象的程序设计

  • 与结构化程序设计相比,更符合人类认识现实世界的思维方式
  • 已成为程序设计的主流方式
  • 涉及的抽象概念:抽象,封装,继承,多态

1.面向对象的程序设计方法概述

对象

现实世界中,万物皆对象,都具有各自的属性,对世界都呈现各自的行为

程序中,一切都是对象,都具有标识,属性和行为(方法),通过一个或多个变量来保存其状态,通过方法实现他的行为。

将属性及行为相同或相似的对象归为一类

类可以看成是对象的抽象,代表了此类对象所具有的共同属性和行为

在面向对象的程序设计中,每一个对象都属于某个特定的类

结构化程序设计

通常由若干个程序模块组成,每个程序模块都可以是子程序或函数

数据和功能分离,代码难于维护和复用

面向对象程序设计

基本组成单位是类

程序在运行时由类生成对象,对象是面向对象程序的核心

对象之间通过发送消息进行通信,互相协作完成相应功能

1.抽象

抽象:忽略问题中与当前目标无关的方面,以便更充分地注意与当前目标有关的方面。

过程抽象:将整个系统的功能划分为若干部分,强调功能完成的过程和步骤,而隐藏其具体的实现。 C语言的函数,Java语言的方法。

数据抽象:面向对象软件开发方法的主要特点。 将系统中需要处理的数据和这些数据上的操作结 合在一起,抽象成不同的抽象数据类型—类。类 既包括数据,也包括对数据的操作。

2.封装

封装:

是一种信息隐蔽技术;

利用抽象数据类型将数据和基于数据的操作封装在一起;

用户只能看到对象的封装界面信息,对象的内部细节对用户是隐蔽的;

封装的目的在于将对象的使用者和设计者分开,使用者不必知道行为实现的细节,只需使用设计者提供的消息来访问对象。

封装的定义:清楚的边界(所有对象的内部信息被限定在这个边界内);接口(对象向外界提供的方法,外界可以通过这些方法与对象进行交互);受保护的内部实现(功能的实现细节,不能从类外访问)。

类的示意图,体现了封装和数据抽象。

image-20210817201512843

3.继承

是指新的类可以获得已有类(称为超类、基类或父类)的属性和行为,称新类为已有类的派生类(也称为子类

在继承过程中派生类继承了基类的特性,包括方法和实例变量

派生类也可修改继承的方法或增加新的方法,使之 更适合特殊的需要

有助于解决软件的可重用性问题,使程序结构清晰, 降低了编码和维护的工作量

单继承

任何一个派生类都只有单一的直接父类

类层次结构为树状结构

多继承

一个类可以有一个以上的直接父类

类层次结构为网状结构,设计及实现比较复杂

Java语言仅支持单继承

对象的实体构成示意图(假设父类可以实例化,也就是父类不是抽象类)

image-20210817201533060

4.多态

一个程序中同名的不同方法共存

主要通过子类对父类方法地覆盖来实现

​ 接口方法覆盖、方法重载也是实现多态的具体形式。

不同类的对象可以响应同名的消息(方法),具体的实现方法却不同

使语言具有灵活、抽象、行为共享、代码共享的优势,很好地解决了应用程序方法同名问题

二、类与对象

在程序中,对象是通过一种抽象数据类型来描述的, 这种抽象数据类型称为类(Class)

一个类是对一类对象的描述。类是构造对象的模板

对象是类的具体实例

1.类的声明

声明形式 [public] [abstract] [final] class类名称 [extends 父类名称] [implements 接口名称列表]

​ {

​ 变量成员声明及初始化;

​ 方法声明及方法体;

​ }

关键字

class 表明其后声明的是一个类。

extends 如果所声明的类是从某一父类派生而来,那么,父类的名字应写在extends之后

implements 如果所声明的类要实现某些接口,那么,接口的名字应写在implements之后

修饰符

  • 可以有多个,用来限定类的方式
    • public 表明此类为公有类
    • abstract 指明此类为抽象类(只能用做超类,不能实例化;只有当子类实现了抽象超类中的所有抽象方法,子类才不是抽象类,才能产生实例)
    • final 指明此类为终结类(终结类不能被继承,终结方法不能被子类覆盖)
  • 类声明体
    • 变量成员声明及初始化 可以有多个
    • 方法声明及方法体 可以有多个

2.对象的声明与引用

变量和对象

变量除了存储基本数据类型的数据,还能存储对象的引用,用来存储对象引用的变量称为引用变量

类的对象也成为类的实例

对象的声明

格式

类名 变量名

声明一个引用变量时并没有对象生成

对象的创建

  • 生成实例的格式:
    • new <类名>()
  • 其作用是:
    • 在内存中为此对象分配内存空间
    • 返回对象的引用(reference,相当于对象的存储地址)
  • 引用变量可以被赋以空值(默认值也是null)aclock = null;

自动装箱拆箱

Java 5新增特性,基本数据类型的自动装箱拆箱

自动装箱

  • Java 5之前:Integer i = new Integer(3);
  • Java 5:Integer i = 3;

自动拆箱

  • Java 5 之前:int j = i.intValue(); //i为Integer类型 的对象
  • Java 5:int j = i; //i为Integer类型的对象
  • Integer是int的包装类,int则是java的一种基本数据类型

自动装箱拆箱

支持自动装箱和自动拆箱的类型

这些都是基本数据类型的包装类

image-20210817201559903

3.数据成员

表示Java类的状态

声明数据成员必须给出变量名及其所属的类型,同时还可以指定其他特性

在一个类中成员变量名是唯一的

数据成员的类型可以是Java中任意的数据类型(简单类型,类,接口,数组)

声明格式

[public | protected | private] [static] [final] [transient] [volatile] 变量数据类型 变量名1[=变量初值],变量名2[=变量初值],…;

格式说明

  • public、protected、private 为访问控制符
  • static指明这是一个静态成员变量
  • final指明变量的值不能被修改
  • transient指明变量是临时状态(不必持久化(serialize))
  • volatile指明变量是一个共享变量

实例变量

没有static修饰的变量称为实例变量

用来存储所有实例都需要的属性信息,不同实例的属性值可能会不同

可通过下面的表达式访问实例属性的值 <实例名>.<实例变量名>

实例变量属于特定的对象,在创建对象时存储在堆中

image-20210817201649113

public class Circle { 
int radius;
}
public class ShapeTester {
public static void main(String args[]) {
Circle x;
x = new Circle();
System.out.println(x);
System.out.println("radius = " + x.radius);
}
}

image-20210817201708120

类变量

也成为静态变量,声明时需加static修饰符

不管类的对象有多少,类变量只存在一份,在整个类中只有一个值

类初始化的同时就被赋值

适用情况:类中所有对象都相同的属性;经常需要共享的数据;系统中用到的一些常量

引用格式 <类名 | 实例名>.<类变量名>

public class Circle { 
static double PI = 3.14159265;
int radius;
}
public class ClassVariableTester {
public static void main(String args[]) {
Circle x = new Circle();
System.out.println(x.PI);
System.out.println(Circle.PI);
Circle.PI = 3.14;
System.out.println(x.PI);
System.out.println(Circle.PI);
}
}

当我们生成Circle类的实例时,在每一个实例中并 没有存储PI的值,PI的值存储在类中

image-20210817201741823

final修饰符

实例变量和类变量都可以被声明为final

final实例变量必须在每个构造方法结束之前赋初值,以保证使用之前会被初始化

final类变量必须在声明的同时初始化

方法参数也可以被声明为final,防止在方法体中给参数重新赋值

​ 不给参数重新赋值是比较好的编码方式。因为可能会引起误会。

实例变量即使被声明为final,也是保存在堆中

Review

▫ 抽象,封装,继承,多态

▫ 自动装箱和自动拆箱

▫ static修饰类的成员变量(Java中方法的局部变量不能是static修饰的). ➔类变量

▫ final修饰类的成员。也是实例变量,在new对象的时候会和其他实例变量一起分配空间。

▫ final 修饰方法参数,防止方法内部对其重新赋值而引起误解。

▫ final修饰方法局部变量:作为常量。

▫ 变量的位置:堆和栈。

4.方法成员

定义类的行为。一个对象能够做的事情,我们能够从一个对象中取得的信息

可以没有,也可以有多个;一旦在类中声明了方法,它就成为了类声明的一部分

分为实例方法和类方法

声明格式

[public | protected | private] [static] [final] [abstract] [native] [synchronized]

​ 返回类型 方法名([参数列表]) [throws exceptionList]

{

​ 方法体

}

格式说明

方法修饰

  • public、protected、private 为存取控制符
  • static指明方法是一个类方法
  • final指明方法是一个终结方法
  • abstract指明方法是一个抽象方法
  • native用来集成java代码和其它语言的代码
  • synchronized用来控制多个并发线程对共享数 据的访问

返回类型

  • 方法返回值的类型,可以是任意的Java数据类型
  • 当不需要返回值时,返回类型为void

参数类型

  • 简单数据类型,
  • 引用类型(数组、类或接口)
  • 可以有多个参数,也可以没有参数,方法声明时的参数称为形式参数

方法体

  • 方法的实现
  • 包括局部变量的声明以及所有合法的Java指令
  • 局部变量的作用域只在该方法内部

throws exceptionList

  • 用来处理异常

方法调用

给对象发消息意味者调用对象的某个方法

  • 从对象中取得信息
  • 修改对象的状态或进行某种操作
  • 进行计算及取得结果等

调用格式

<对象名>.<方法名>([参数列表])

称点操作符“.”前面的<对象名>为消息的接收者

参数传递

  • 值传递:参数类型为基本数据类型时
  • 引用传递:参数类型为引用变量时(比如对象类型或数组时)

实例方法

表示特定对象的行为

声明时前面不需要加上static修饰符

使用时需要发送给一个类实例

关键字this代表此方法的接收者对象

不同的类中可以声明相同方法名的方法 ;使用时,系统会根据接收者对象的类型找到相应类的方法

类方法

也成为静态方法,表示类中对象的共有行为

声明时前面需加static修饰符

不能被声明为抽象的

类方法可以在不建立对象的情况下用类名直接调用,也可用类实例调用。

类方法中不能访问实例变量,否则会发生编译错误

可变长参数

从Java 5开始,可以在方法的参数中使用可变长 参数

可变长参数使用省略号表示,其实质是数组

例如,”String … s”表示”String[] s”

对于可变长参数的方法,传递给可变长参数的实际参数可以是多个对象,也可以是一个对象或者是没有对象

static double maxArea(Circle c, Rectangle... varRec) {
Rectangle[] rec = varRec;
for (Rectangle r : rec) {
}
}
public static void main(String[] args) {
Circle c = new Circle();
Rectangle r1 = new Rectangle();
Rectangle r2 = new Rectangle();
System.out.println("max area of c, r1 and r2 is " + maxArea(c, r1,
r2));
System.out.println("max area of c and r1 is " + maxArea(c, r1));
System.out.println("max area of c and r2 is " + maxArea(c, r2));
System.out.println("max area of only c is " + maxArea(c));
}

5.类的组织

包的概念

是一组类的集合,一个包可以包含若干个类文件,还可以包含若干个包

包的作用:

  • 将相关的源代码文件组织在一起
  • 类名的空间管理,利用包来划分名字空间,便可以避免类名冲突
  • 提供包一级的封装及存取权限

包的命名

  • 每个包的名称必须是“独一无二”的
  • Java中包名使用小写字母表示
  • 命名方式建议
    • 将机构的Internet域名反序,作为包名的前导
    • 若包名中有任何不可用于标识符的字符,用下划线替代
    • 若包名中的任何部分与关键字冲突,后缀下划线
    • 若包名中的任何部分以数字或其他不能用作标识符 起始的字符开头,前缀下划线

编译单元与类空间

  • 一个Java源代码文件称为一个编译单元,由三部分组成
    • 所属包的声明(省略,则属于默认包)
    • Import(引入)包的声明,用于导入外部的类
    • 类和接口的说明
  • 一个编译单元中只能有一个public类,该类名与文件名相同,编译单元中的其他类往往是public类的辅助类,经过编译,每个类产生一个class文件
  • 利用包来划分空间,便可以避免类名冲突

包的声明

  • 命名的包 例如:package Mypackage;
  • 默认包 不含有包声明的编译单元是默认包的一部分

包与目录

  • Java使用文件系统来存储包和类
  • 包名就是文件夹名,即目录名
  • 目录名并不一定是包名
  • 用javac编译源程序时,如遇到当前目录(包)中没有声明的类,就会以环境变量classpath为相对查 找路径,按照包名的结构来查找。因此,要指定 搜寻包的路径,需设置环境变量classpath

引入包

  • 为了使用其它包中所提供的类,需要使用import语句引入所需要的类
  • Java编译器为所有程序自动引入包java.lang
  • import语句的格式 import package1[.package2…]. (classname |*);
    • 其中package1[package2…]表明包的层次,它对应于文件目录
    • classname则指明所要引入的类名
    • 如果引入一个包中的所有类,则可以使用星号(*)来代替类名

静态引入

  • Java5新特性
    • 在Java 5之前,通过类名使用类的静态成员。例如, Math.PI,Math.sin(double)
    • 如果在程序中需要多次使用静态成员,则每次使用都 需要加上类名
  • 静态引入分为两种:单一引入,全体引入
    • 单一引入是指引入某一个指定的静态成员,例如: import static java.lang.Math.PI;
    • 全体引入是指引入类中所有的静态成员,例如: import static java.lang.Math.*;

程序编译方法

javac -d . Person.java `` javac -d . Student.java

这样编译器会自动创建目录并保存class文件

如果当前位置不在上述编译程序的目录下,可以 利用classpath指定JVM搜索类文件的路径。比如: java -classpath cn.edu.nwpu.person.Student

6.访问控制

类的访问控制

体现封装和细节隐藏的程度

类的访问控制只有public及无修饰符(缺省类)两种

访问权限符与访问能力之间的关系如表image-20210817201819831

类成员的访问控制

公有(public)可以被其他任何对象访问(前提是对类成员所在类有访问权限)

保护(protected)可被同包任何类,同一类及其子类的实例对象访问

私有(private)只能被这个类本身访问,在类外不可见

默认(default)仅允许同一个包内访问:又被称为“包访问权限”

image-20210817201854023

面向对象程序设计为了体现细节隐藏,应该尽可能把数据成员设计为private。

如果要允许其它类访问radius的值,就需要在Circle类中声明 相应的公有方法。通常有两类典型的方法用于访问属性值, get方法及set方法

get方法

功能是取得属性变量的值

get方法名以“get”开头,后面是实例变量的名字

一般具有以下格式: public get(){return ;}

set方法

功能是修改属性变量的值

set方法名以“set”开头,后面是实例变量的名字

一般具有以下格式:public void set( )

​ {=;}

关键字this的使用

如果形式参数名与实例变量名相同,则需要在实例变量名之前加this关键字,否则系统会将实例变量当成形式参数。

在上面的set方法中,如果形式参数为radius,则需要在成员变量radius之前加上关键字this。

public void setRadius(int radius){ this.radius = radius; }

Review

  • 实例方法,类方法

    • 类方法不能访问实例变量
  • • package

    • 类的组织和管理
    • classpath 的使用
    • import 以及import static
  • 访问控制

  • 类的访问控制: public 默认

  • 类成员的访问控制: public 默认, protected, private

  • set和get方法:

Package补充

Alpha类的访问控制 为public,则其成员的可见性:

image-20210817201911757

三、对象的初始化和回收

对象的初始化

系统在生成对象时,会为对象分配内存空间,并自动调用构造方法对实例变量进行初始化

对象回收

对象不再使用时,系统会调用垃圾回收程序将其占用的内存回收

1.构造方法

一种和类同名的特殊方法;

用来初始化对象;

Java中每个类都有构造方法,用来初始化该类的一个新的对象;

没有定义构造方法的类,系统自动提供默认的构造方法。

构造方法的特点:

  • 方法名与类名相同
  • 没有返回类型,修饰符void也不能有
  • 通常被声明为公有的(public)
  • 可以有任意多个参数
  • 主要作用是完成对象的初始化工作
  • 不能在程序中显式的调用
  • 在生成一个对象时,系统会自动调用该类的构造方法为新生成的对象初始化

默认构造方式

系统提供的默认构造方式

  • 如果在类的声明中没有声明构造方法,则Java编译 器会提供一个默认的构造方法
  • 默认的构造方法没有参数,其方法体为空
  • 使用默认的构造方法初始化对象时,如果在类声明中没有给实例变量赋初值,则对象的属性值为零或空

自定义构造方法

自定义构造方法与方法重载

  • 可在生成对象时给构造方法传送初始值,使用希望的值给对象初始化
  • 构造方法可以被重载,构造方法的重载和方法的重载一致
  • 一个类中有两个及以上同名的方法,但参数表不同,这种情况就被称为方法的重载。在方法调用时,Java可以通过参数列表的不同来辨别应调用哪一个方法。

自定义无参的构造方法

  • 无参的构造方法对其子类的声明很重要。如果在一个类中不存在无参的构造方法,则要求其子类声明时必须声明构造方法,否则在子类对象的初始化时会出错。
  • 在声明构造方法时,好的声明习惯是
    • 不声明构造方法
    • 如果声明,至少声明一个无参构造方法

用户在进行类声明时,如果没有声明任何构造方法,系统 会赋给此类一个默认(无参)的构造方法。但是,只要用 户声明了构造方法,即使没有声明无参的构造方法,系统也不再赋默认的构造方法。

this关键字的使用

可以使用this关键字在一个构造方法中调用另外的构造方法;

代码更简洁,维护起来更容易;

通常用参数个数比较少的构造方法调用参数个数最多的构造方法

2.内存回收技术

内存回收技术

当一个对象在程序中不再被使用时,就成为一个无用对象

  • 当前的代码段不属于对象的作用域
  • 把对象的引用赋值为空

Java运行时系统通过垃圾收集器周期性地释放无用对象所使用的内存

Java运行时系统会在对对象进行自动垃圾回收前,自动调用对象的finalize()方法

垃圾收集器

自动扫描对象的动态内存区,对不再使用的对象做上标记以进行垃圾回收

作为一个线程运行

  • 通常在系统空闲时异步地执行
  • 当系统的内存用尽或程序中调用**System.gc()**要求进行垃圾收集时,与系统同步运行。

finalize()方法

在类java.lang.Object中声明,因此 Java中的每一个 类都有该方法

用于释放系统资源,如关闭打开的文件或socket

声明格式 protected void finalize() throws throwable

如果一个类需要释放除内存以外的资源,则需在类中重写finalize()方法(不可靠)

与C++析构函数不同,finalize()方法在垃圾回收时才会调用。注意:

  • 对象不一定会被回收
  • 垃圾回收不是析构函数
  • 垃圾回收至于内存有关
  • 垃圾回收和finalize()都是靠不住的,因为系统执行垃圾回收的时机不确定

同C和C++的区别

C语言中通过free来释放内存,C++中则通过delete来释放内存

在C和C++中,如果程序员忘记释放内存,则容易造成内存泄漏甚至导致内存耗尽

在Java中不会发生内存泄漏情况,但对于其它资源, 则有产生泄漏的可能性

四、枚举类型

Java 5的新特色,可以取代Java 5之前的版本中使用的常量

需要一个有限集合,而且集合中的数据为特定的值时,可以使用枚举类型

格式:

[public] enum 枚举类型名称 [implements 接口名称列表]

{

​ 枚举值;

​ 变量成员声明及初始化;

​ 方法声明及方法体;

}

枚举类型特点

枚举类型是类,而不是简单的整数类型,枚举值是类的对象。

枚举类型是java.lang.Enum类的子类。

枚举类型没有public的构造函数

枚举值是public、static、final的。

1.枚举类型的默认方法

  • 取得枚举值的数组
    • public static T[] values()
  • 取得枚举值对应的字符串
  • public String toString()
  • 取得对象在枚举类型中的索引
  • public final int ordinal()
  • 字符串转换为枚举值。
  • public static T valueOf(String)

2.枚举类型的自定义属性和方法

枚举类型相当于自定义一个类。因此可以给该类自定义数据和方法。

枚举类型的构造函数默认是private,而且必须是private。

即枚举类型会由JVM在加载的时候,实例化枚举对象,你在枚举类中定义了多少个就会实例化多少个,JVM为了保证每一个枚举类元素的唯一实例,是不会允许外部进行new的,所以会把构造函数设计成private,防止用户生成实例,破坏唯 一性。

因为枚举对象的实例化是由jvm完成的,所以可 以确保该对象只被创建一次。因此,利用枚举可以完美的实现“单例模式”。这是目前最有效的 单例模式实现方法。

补充材料:变量初始化

变量声明时可以设定初值,比如: class Car { int door=4; }

可以在构造函数中设置初值,比如:class Car {Car(){door=5;}}

实例变量的初始化块。可以把构造函数中共同的处理放到初始化块中。编译器会自动地把初始化块的代码插入到构造函数最前面

初始化块可以写多个。image-20210518193854367

对于类变量,可以使用静态初始化块。静态初始化块会在类加载时执行

静态初始化块可以有多个,会按照代码顺序执行。

image-20210518194028091

执行顺序:变量初始化最先执行。

  • 在加载类时执行一次静态初始化块(之后不再调用)
  • 在每次初始化实例对象时:先执行非静态初始化块,在执行构造方法。

Review

构造方法

  • 没有返回值
  • 默认构造方法
  • 重载: 方法签名(method signature )

内存回收

  • 变量的自动释放
  • 显式地给引用变量赋值null
  • finalize()方法由垃圾回收器执行,执行时机不确定,因此不可靠。

枚举

  • 特殊的类,构造方法总是private的
  • 枚举值是枚举类型的实例,加载类时由jvm创建(单例模式)

变量初始化

  • 实例变量:初值→初始化块→构造方法
  • 类变量: 初值→静态初始化块

五、应用举例

七、注解

注解也叫元数据,就是用来描述数据的数据。它其实就是程序代码里的特殊标记,这些标记可以在编 译、类加载、运行时被读取并执行相应的处理。注 解主要用于告知编译器要做什么事情,在程序中可 对任何程序元素进行注解。

根据注解的作用可以将注解分为基本注解、元注解 (或称元数据注解)与自定义注解三种

注解可以理解为对代码贴的标签,这个标签对 代码进行说明和解释。不过这个标签和代码的 注释(comment)不同:

  • 注释只存在于代码中,编译器会简单地跳过注释。
  • 而编译器会处理注解。而且根据注解自身的特点,可以保留到运行时的内存中。

基本注解:Java提供的注解。主要有三种:

  • java.lang.Override: 重载父类的方法
  • java.lang.Deprectated: 方法已过时
  • java.lang.SuppressWarnings: 抑制编译器警告

1.自定义注解

格式:

[public | ] [abstract | final] @interface 注解名 { 元素定义; }

两类特殊注解

标记注解:没有元素定义

单值注解:只定义一个元素

注解的使用:在注解名前加上”@“符号,并在其后的括号中对个元素赋值

@interface MyMarkerAnnotation { }
@interface MySingleValueAnnotation {
String value ( );
}
@interface MyAnnotation {
String value();
int i();
float f() default 2.0f;
double d();
}
public class AnnotationTester {
public static void main(String[] args) { }
@Override //表示覆盖父类的方法
public String toString() {
return "";
}
@MyMarkerAnnotation
public void method1() {
}
@MySingleValueAnnotation("s")
public void method2() {
}
@MyAnnotation(value="s", i=1, d=3.0)
public void method3() {
}
@MyAnnotation(value="s", i=1, f=2.1f, d=3.0)
public void method4() {
}
}

2.元注解简洁

元注解:注解的注解

java.lang.annotation包下,提供了4个元注解:

  • Retention:表明注解的保留程度,需要提供一个 java.lang.annotation.RetentionPolicy枚举类型的枚举值
    • RetentionPolicy.SOURCE RetentionPolicy.CLASS RetentionPolicy.RUNTIME
  • Target:指定注解所适用的程序元素的类型,需要提供一个java.lang.annotation.Target枚举类型的枚举值:
    • ANNOTATION_TYPE , CONSTRUCTOR , FIELD , LOCAL_VARIABLE , METHOD , PACKAGE , PARAMETER , TYPE , and TYPE_PARAMETER
    • 从Java 8开始,注解已经能应用于任何目标。这其中包括 new操作符、类型转换、instanceof检查、泛型类型参数, 以及implements和throws子句。
  • Documented:表明可以将注解通过Javadoc或者类似工具进行文档化
  • Inherited:表明注解被自动继承

3.注解的处理

从Java 6开始,可以对注解进行处理, javax.annotation.processing包提供了对注解的处理

八、本章小结

本章内容

  • 面向对象程序设计的基本概念和思想
  • Java语言类与对象的基本概念和语法,包括类的声明、类成员的访问,以及对象的构造、初始化和回收

本章要求

  • 理解类和对象的概念
  • 熟练使用类及其成员的访问控制方法
  • 熟练掌握各种构造方法
  • 了解java的垃圾回收机