构造方法与匿名对象
程序在使用类的时候按照以下步骤进行:
- 声明并实例化对象:这个时候实例化对象中的属性没有任何的数据,都是其对应数据的默认值。
- 需要通过一系列的setter方法为类中的属性设置内容
public class JavaDemo{
public static void main(String [] args)
{
Person per=new Person();
//对象的初始化准备。
per.setName("张三");
per.setAge(18);
//对象的基本操作
per.tell();
}
}
如果现在有8个属性,那么调用实例化方法就是8个,这样调用太为复杂。,所以现在提供有构造方法,可以通过构造方法
实现实例化对象中的属性初始化处理。
只有在关键字new的时候才使用构造方法。
构造方法要求如下:
- 方法名称必须与类名称保持一致。
- 构造方法不允许设置任何返回值类型,即没有返回值定义。
- 构造方法是在使用关键字new实例化对象的时候自动调用的。
定义构造方法
class Person{
private String name ;
private int age;
//方法名称与类名称相同,并且无返回值定义。
public Person (String n,int a)
{
name=n;
age=a;
//为属性赋值(初始化)
}
public void tell()
{
System.out.println("姓名:"+name+" 年龄:"+age);
}
}
class JavaDemo{
public static void main(String [] args)
{
Person per=new Person("张三",18);
//对象的初始化准备,传递参数进去
per.tell();
}
}
下面针对当前的对象实例化格式与之前的对象实例化格式做一个比较:
之前的对象实例化格式:Person per=new Person();
当前的对象实例化格式:Person per=new Person("张三",18);
- Person主要是定义对象的所属类型,类型决定了你可以调用的方法。
- per 实例化对象的名称,所有操作通过对象进行访问。
- new 开辟一块新的堆内存空间
- Person(“张三”,18); 调用有参构造方法。
- Person(); 调用无参的构造方法。
在java程序里面考虑到程序的完整性,所以所有的类都会提供有构造方法,如果类里面没有书写构造方法,那么一定会默认提供有一个无参的什么都不做的构造方法,这个构造方法是在程序编译的时候自动创建的。
已经在类中定义了一个构造方法,那么这个默认的构造方法将不会被自动创建。
结论:一个类至少存在有一个构造方法,永恒存在。
为什么构造方法上不允许设置返回值类型??既然没有返回值,为什么不采用void来定义??
分析:
程序编译器是根据代码结构来编译处理的,执行的时候也是根据代码结构来处理的。如果在构造方法上使用了void,那么就与我们的普通方法结构相同,那么编译器会把它看成一个普通方法。
普通方法与构造方法的最大区别:构造方法是在类对象实例化的时候调用的,而普通方法是在类对象产生之后调用的。
既然构造方法本身是一种方法,那么方法就具有重载的
特点。而构造方法重载的时候只需要考虑参数的类型及个数即可。
public Person () { }
//构造
public Person (String n)//重载
{
name=n;
}
重新修改一下:
public Person () {
name="1223";
age=22;
}
public Person (String n)
{
name=n;
}
此时的结果:
在进行多个构造方法定义时有一些定义的顺序:可以按照参数的个数降序或者升序排列。
经过分析可以发现,构造方法的确是可以进行数据的设置,而对于setter也可以进行数据的设置,这个时候一定要清楚,构造方法是在对象实例化的时候为属性初始化内容
,而setter除了拥有设置数据的功能外还具有修改数据的功能。
范例:使用setter修改数据。
Person per=new Person("李四",22);
per.setName("张三");
per.setAge(18);
per.tell();
经过分析之后,利用构造方法可以传递属性数据,进一步分析对象产生格式。
- 定义对象的名称:
类名称 对象名称 = null
- 实例化对象:
对象名称 = new 类名称()
如果这个时候只是通过实例化对象来进行类的操作也是可以的,而这种形式的对象没有名字,就叫做匿名对象
。
范例:观察匿名对象
public class JavaDemo{
public static void main(String [] args)
{
new Person("张三",18).tell();
//这是一个完整的对象;
}
}
此时依然进行了tell()方法的调用,由于这个对象没有任何的引用名称,所以该对象使用一次之后就将成为垃圾,而所有的垃圾将被GC进行回收和释放。
现在发现程序里面已经存在有构造方法了,那么下面通过一个程序来利用构造方法来进行内存分析
范例:编写一个分析程序。
class Message{
private String title;
public Message(String t){
title=t;
}
public String getTitle()
{
return title;
}
public void setTitle(String t)// 具有修改功能;
{
title=t;
}
}
class Person{
private String name ;
private int age;
public Person (Message msg,int a)
{
name=msg.getTitle();
age=a;
}
public Message getInfo()
{
return new Message(name+" "+age);
}
public void tell()
{
System.out.println("姓名:"+name+" 年龄:"+age);
}
}
public class JavaDemo{
public static void main(String [] args)
{
Message msg=new Message("mldn");
Person per=new Person(msg,20);
msg=per.getInfo();
System.out.println(msg.getTitle());
}
}
通过此程序进行一个简短的内存分析:
只要是方法就可以传递任意的数据类型,包括基本数据类型和引用数据类型。