ate*_*iob 18 java getter getter-setter
在C++中,私有数据成员的getter和setter非常有用,因为它能够通过const返回值控制可变性.
在Java中,如果我理解正确(如果我弄错了请纠正我),final在getter上指定不会那样.一旦调用者通过getter接收到数据成员引用,它就可以修改它,尽管它是私有的......
如果是这种情况(如果我在这里有严重的误解,请纠正我),为什么不宣布数据成员public并简化事情呢?
Joh*_*erg 25
使得immutable在java中的返回值是的问题要么返回已经immutable对象类型(如字符串)或返回一个副本非不可变对象.
示例1 - 已经是不可变对象
public String getValue() {
return value;
}
Run Code Online (Sandbox Code Playgroud)
示例2 - 已经不可变对象的集合
public List<String> getValues() {
return new ArrayList<String>(values);
}
Run Code Online (Sandbox Code Playgroud)
示例3 - 非不可变对象
public Complex getComplex() {
return complex.clone();
}
Run Code Online (Sandbox Code Playgroud)
示例4 - 非不可变对象的集合
public List<Complex> getComplex() {
List<Complex> copy = new ArrayList<Complex>(complexs.size());
for (Complex c : complexs)
copy.add(c.clone());
return copy;
}
Run Code Online (Sandbox Code Playgroud)
样本3和4是基于复杂类型实现Cloneable接口的便利性.
此外,为了避免子类重写不可变方法,您可以声明它们final.作为旁注,该builder模式通常用于构造不可变对象.
如果您希望您的类是不可变的(即只有final字段和getter),您必须确保返回的值也是不可变的.返回Strings和内置基元时可以免费获得,但是其他数据类型需要一些额外的步骤:
Date和Calendarclone它们.这也适用于集合中的对象.请注意,如果您防御性地复制集合,客户端可以查看或修改副本,但这不会影响原始集合:
return new ArrayList<Foo>(foos);
Run Code Online (Sandbox Code Playgroud)
另一方面,如果您包装原始集合,客户端能够看到在创建包装器之后引入到集合的所有更改,但尝试更改包装器的内容将导致运行时异常:
return Collections.unmodifiableList(foos);
Run Code Online (Sandbox Code Playgroud)
底线是:Foo必须也是不可变的,否则集合是不可变的,但客户端代码仍然可以修改集合的成员.所以同样的规则适用于Foo.
如果是这种情况(如果我在这里有严重的误解,请纠正我),为什么不公开数据成员并简化事情呢?
因为:
| 归档时间: |
|
| 查看次数: |
8763 次 |
| 最近记录: |