不推荐使用第二种方法
第二个例子不推荐使用,因为如果您向Address类中添加新字段,则您是将其添加到现有的setter方法中还是创建一个新的setter方法?如果将其添加到现有的setter方法中,则调用该方法的任何类都将被破坏。如果创建一个新的setter方法,则对于想要使用该类的人来说,为什么某些字段以这种方式分组而其他字段则不是会感到困惑。
为要公开的每个字段使用单独的setter方法
常见的做法是为要公开的每个字段在类中拥有一个单独的setter方法(即第一个示例)。是否这是一种好的做法存在争议,因为它强制使一个类可变。如果可能,最好使对象不可变,原因有很多,详见此处。
使用构造函数初始化字段
使类不可变的一种方式是去掉setter方法,而是通过类构造函数设置字段,如下所示。以这种方式实现的缺点是,如果您的类有很多字段,可能会导致构造函数调用变得很长,难以阅读。
public class Address {
public String name;
public String city;
private Address(String name, String city) {
this.name = name;
this.city = city;
}
}
使用构建器模式初始化您的字段
下面是一个完全不同的实现(灵感来自于这篇文章),它是构建器模式的一种变体。它模拟了对象的可变性而不牺牲可读性。
public class Address {
public String name;
public String city;
private Address() {}
private void setName(String name) {
this.name = name;
}
private void setCity(String city) {
this.city = city;
}
static class Builder {
private Address address = new Address();
public Builder name(String name) {
address.setName(name);
return this;
}
public Builder city(String city) {
address.setCity(city);
return this;
}
public Address build() {
return address;
}
}
}
使用上述类,您可以按照以下方式创建Address类的不可变实例:
Address address = new Address.Builder()
.name("Mansoor's address")
.city("Toronto")
.build();
哪种方法使用的内存更多?
从内存角度来看,由于类在内存中的大小取决于类中的字段,因此不应该有任何区别。 由于所有三种实现都具有相同的字段,无论使用哪种方法,它们都应该占用相同的内存空间。