1.如果一个类始终只能创建一个实例,则这个类被称为单例类。
思路:public static void main(String[] args)不创建实例,而是引用类中方法内创建的实例。
创建一个新对象,使用new,就要使用构造函数。既然是单例,就不能使用构造函数来创建(于是将类中构造函数权限设置为private),只能引用已有的,用getClassname去调用类中方法中创建的仅有只有的一个实例。没有new对象,而在public static void main(String[] args)静态上下文要引用静态方法,则类名.method,必须static。
class Animal
{
private static Animal instance;
private Animal(){};
public static Animal getAnimal()
{
if(instance == null)
{
instance = new Animal();
}
return instance;
}
}
public class PrivateFinalMethodTest
{
public static void main(String[] args)
{
Animal a = Animal.getAnimal();
Animal b = Animal.getAnimal();
System.out.println(a == b);
}
}
2.不可变类
final修饰引用对象的变量,则变量指向的对象地址不变,但是对象的内容可以变化。final int[] iArr = {1,3,2,4},可以赋值iArr[1] = 5,改变对象的内容。而在很多时候,需要类的内容也不可变。例如,创建一个人的类的实例,若名字作为主键,则名字必须不可变。
在Person、Name类中,主类为Person。在主类中,创建一个private final Name name来保存Name类的名字实例Name name,但两者不能指向同一个地址,也就是不能引用同一个对象,在赋值的时候,需要new一下,那么在改动Name name中的量,无关private final Name name。同样在获取的时候,直接用private final Name name来代替Name name。
class Name
{
private String firstName;
private String lastName;
public Name(){}
public Name(String firstName,String lastName)
{
this.firstName = firstName;
this.lastName = lastName;
}
public void setFirstName(String firstName)
{
this.firstName = firstName;
}
public void setlastName(String firstName)
{
this.lastName = lastName;
}
public String getFirstName()
{
return this.firstName;
}
public String getLastName()
{
return this.lastName;
}
}
public class Person
{
private final Name name;
/*
public Person(Name name)
{
this.name = name;
}
public Name getName()
{
return name;
}
*/
public Person(Name name)
{
this.name = new Name(name.getFirstName(),name.getLastName()); //两者引用不同的对象,地址不同,但是内容相同
}
public Name getName()
{
//return new Name(name.getFirstName(),name.getLastName());
//在获取时用private final Name name,而不是Name name。直接return this.name也一样,没必要new一下。
return this.name;
}
public static void main(String[] args)
{
Name n = new Name("Genz","ZHANG");
Person p =new Person(n);
System.out.println(p.getName().getFirstName());
n.setFirstName("bajie"); //改变Name n的内容,无关this.name的内容
System.out.println(p.getName().getFirstName()); //private final Name name未变
System.out.println(n.getFirstName()); //Name n的内容改变
}
}