有些代码中只有实例域,没有方法,只是为了存放数据时用的退化类。这样的类非常不好,因为没有封装功能,无法对域添加约束。
class Point{
public double x;
public double y;
}
如果坚持面向对象编程,应该使用私有域,如果可以被访问的话用公有方法(getter)访问,如果可以改变值,使用(setter)方法代替,如果类可以在所在的包外访问,就提供访问方法,如果公有类暴露了数据域的,要想在内部对其改变是不可能的,因为公有类的客户端代码已经到处都是了!
class Point{
private double x;
private double y;
public Point(double x, double y){
this.x = x;
this.y = y;
}
public double getX(){return x;}
public double getY(){return y;}
public void setX(double x){this.x = x;}
public void setY(double y){this.y = y;}
}
如果类是包级私有的或者是私有的嵌套类,直接暴露数据域没有什么本质错误。
Java平台类库中的几个类违反了公共类不应直接暴露属性的建议。 着名的例子包括java.awt包中的Point
和Dimension
类。 这些类别应该被视为警示性的示例,而不是模仿的例子。 如条目 67所述,暴露Dimension
的内部结构的决定是一个严重的性能问题,这个问题在今天仍然存在。
总结:公有类永远不应该暴露可变域,虽然还是有问题,但是可以适当暴露不可变的域,相对危害小一点。但是有时会需要用包级私有或者私有的嵌套类暴露于,无论这个类是可变还是不可变的。