一.构造方法
在实例化一个对象后,如果要为这个对象中的属性赋值,则必须用setter方法为属性分别赋值才可以,这显然不够方便。这时可以通过构造方法来完成这样的操作。在面向对象中构造方法的主要作用是为类中的属性初始化。
构造方法可以看成为一种特殊的方法:
【构造方法的定义格式】
class 类名称{
访问权限 类名称(类型1 参数1,类型2 参数2,…….){
…….//构造方法没有返回值
}
}
在构造方法时要注意:
*构造方法的名称必须与类名称一致;
构造方法的声明处不能有任何返回值类型的声明;
不能在构造方法中使用return返回一个值;*
声明一个构造方法:
class Person{
public Person(){ // 声明构造方法
System.out.println("一个新的Person对象产生。") ;
}
};
public class ConsDemo01{
public static void main(String args[]){
System.out.println("声明对象:Person per = null ;") ;
Person per = null ; // 声明对象时并不去调用构造方法
System.out.println("实例化对象:per = new Person() ;") ;
per = new Person() ;//实例化对象
}
};
运行结果:
声明对象:Person per = null ;
实例化对象:per = new Person() ;
一个新的Person对象产生。
程序实例化对象的过程与之前一样的,在类中定义一个person类的构造方法,但是从程序的运行结果来看,当调用关键字new实例化对象时才会调用构造方法。
在上例中,类中并没有构造方法,但是也可以调用,只是为什么?首先要说明的是,只要是类就必定存在构造方法,在Java中如果一个类中没有明确的声明一个构造方法时,则在编译时会直接生成一个无参数、什么都不做的构造方法,也就是说,如果以上的Person类中没有声明构造方法,实际上编译时会在动加上以下的构造方法:
class Person{
public Person(){}
}
下面用构造方法进行复制
class Person{
private String name ;
private int age ;
public Person(String n,int a){ // 声明构造方法,为类中的属性初始化
this.setName(n) ;
this.setAge(a) ;
}
public void setName(String n){
name = n ;
}
public void setAge(int a){
if(a>0&&a<150){
age = a ;
}
}
public String getName(){
return name ;
}
public int getAge(){
return age ;
}
public void tell(){
System.out.println("姓名:" + this.getName() + ";年龄:" + this.getAge()) ;
}
};
public class ConsDemo02{
public static void main(String args[]){
System.out.println("声明对象:Person per = null ;") ;
Person per = null ; // 声明对象时并不去调用构造方法
System.out.println("实例化对象:per = new Person() ;") ;
per = new Person("张三",30) ;//实例化对象
per.tell() ;
}
};
运行结果为:
声明对象:Person per = null ;
实例化对象:per = new Person() ;
姓名:张三;年龄:30
通过对比可以看出,通过构造方法进行赋值比通过setter方法更加方便。
与普通方法一样,构造方法也是可以重载的,只要每个构造方法的参数类型或参数个数不同,即可实现重载
【构造方法的重载】
class Person{
private String name ;
private int age ;
public Person(){} // 声明一个无参的构造方法
public Person(String n){ // 声明有一个参数的构造方法
this.setName(n) ;
}
public Person(String n,int a){ // 声明构造方法,为类中的属性初始化
this.setName(n) ;
this.setAge(a) ;
}
public void setName(String n){
name = n ;
}
public void setAge(int a){
if(a>0&&a<150){
age = a ;
}
}
public String getName(){
return name ;
}
public int getAge(){
return age ;
}
public void tell(){
System.out.println("姓名:" + this.getName() + ";年龄:" + this.getAge()) ;
}
};
public class ConsDemo03{
public static void main(String args[]){
System.out.println("声明对象:Person per = null ;") ;
Person per = null ; // 声明对象时并不去调用构造方法
System.out.println("实例化对象:per = new Person() ;") ;
per = new Person("张三",30) ;//实例化对象
per.tell() ;
}
};
运行结果为:
声明对象:Person per = null ;
实例化对象:per = new Person() ;
姓名:张三;年龄:30
以上方法被重载了三次,在主方法调用的是只有一个参数的构造方法。
二.匿名对象
匿名对象就是没有明确的给出名称的对象。一般匿名对象只使用一次,而且匿名对象只在堆内存中开辟空间,而不存在栈内存的引用。
【匿名对象的使用】
class Person{
private String name ;
private int age ;
public Person(String n,int a){ // 声明构造方法,为类中的属性初始化
this.setName(n) ;
this.setAge(a) ;
}
public void setName(String n){
name = n ;
}
public void setAge(int a){
if(a>0&&a<150){
age = a ;
}
}
public String getName(){
return name ;
}
public int getAge(){
return age ;
}
public void tell(){
System.out.println("姓名:" + this.getName() + ";年龄:" + this.getAge()) ;
}
};
public class NonameDemo01{
public static void main(String args[]){
new Person("张三",30).tell() ;
}
};
运行结果:
姓名:张三;年龄:30
在上面程序中,直接使用了“new Person(“张三”,30)”语句,这实际上就是一个匿名对象,与之前声明的对象不同,此处没有任何栈内存引用它,所以此对象使用一次之后接等待被垃圾收集机制回收。