Java面向对象软件开发
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

2.1.3 类及类成员的访问权限

Java封装的一大好处就是保护数据,因此要访问类或封装在类中的数据和代码,必须清楚在什么情况下,它们是可访问的,或者我们如何来限制别人的访问。

一个类总可以访问和调用自己的变量和方法,但这个类之外的程序其他部分是否能访问这些变量和方法,则由该属性和方法以及它们所属类的访问控制符决定。

1.类的访问权限

一个类仅有两个可能的访问权限:默认的和公有(public)的。当一个类被声明为public时,该类可被任何包的代码访问;如果一个类为默认的访问权限,那么仅能由同一包内的其他代码所访问。如下定义的Rectangle类为默认访问权限,因此它只能在本身所在的包内被访问。

            class Rectangle{
              ...
            }

2.类成员的访问权限

类成员的访问权限不可能大于类的访问权限。即如果类只能在本包内被访问,那么作为类的成员也最多只能在本包中被访问,就算该成员设定为public也同样受到这个规则的限制。

类成员的可访问性与定义时所用的修饰符private(私有)、default(缺省)、protected(保护)和public(公共)有关。声明为private的类成员仅能在本类内被访问;修饰符在缺省状态,只能被本类和本包访问,声明为protected的类成员可以被本类、本包、本类的子类访问;声明为public的类成员可以被所有包内的类所访问;未用修饰符声明的类成员,则隐含为在本包内可被访问。

为清楚起见,将类成员的可访问性总结在表2-1中。其中,“√”表示允许使用相应的变量和方法。注意,表中列出的类成员可访问性是针对public类的成员。

表2-1 Java类的成员变量和成员方法的访问权限

关于子类的概念在下一节讲解继承性的时候详细讲解。

例2-1】 创建一个包com和其子包bean,将矩形类Rectangle放入该包中;再创建com.demo包,定义RectangleDemo主类并放入com.demo包中,在主方法中使用com.bean包中的Rectangle类,生成一个Rectangle类的对象,打印该对象的信息。

            // 源文件Rectangle.java
            package com.bean;  //本类属于com包的bean子包下
            public class Rectangle{  // 该类的权限为public
                // 私有的成员变量
                private double length;
                private double width;
                // 求长方形的面积,注意该方法权限
                double area(){
                    return length * width;
                }
                /**打印输出,公共的成员方法*/
                public void display(){
                    // 调用当前对象的成员变量
                    System.out.println("长:" + length + "\t宽:" + width);
                    // 调用当前对象的成员方法
                    System.out.println("长方形的面积是:" + area());
                }
            }
            // 源文件RectangleDemo.java
            package com.demo;  // 本类属于com.demo包下
            import com.bean.*;  // 导入com.bean包中所有的类
            public class RectangleDemo{
                public static void main (String args[]){
                    // 调用无参构造方法创建一个长方形对象rect
                    Rectangle rect = new Rectangle();
                    //rect.width=2;  //private不允许类外部调用
                    //rect.length=4;  //private不允许类外部调用
                    //System.out.println("长方形的面积是:"+rect.area());  // 默认权限不同包的类不能调用
                    rect.display();  // 调用对象rect的成员方法
                }
            }

可以看出,在Rectangle类内,方法area()使用默认访问,它只能在本包com.bean内被访问。成员变量length和width被赋予了private访问权,这意味着它不能被Rectangle类外的代码访问,所以在RectangleDemo类内不能直接使用length和width,而public方法display()可以允许其他包的类使用。

3.getter、setter方法

上面的程序引出了一个问题,既然私有属性不能外部访问,那么如何给对象中的私有属性赋值呢?

若需要在其他类中访问私有属性,可以通过非私有的setter和getter方法来访问。这样的方法常命名为setXxx()和getXxx(),分别实现对该私有属性的设置和读取操作。如下编写了对私有属性width和length的setter、getter方法。

            public void setWidth(double w){ // 设置长方形的宽
                width = w;
            }
            public double getWidth(){      // 获取长方形的宽
                return width;
            }
            public void setLength(double l){  // 设置长方形的长
                length = l;
            }
            public double getLength(){     // 获取长方形的长
                return length;
            }

那么,就可以在其他类中利用这两个方法对私有属性进行操作了。

            public class RectangleDemo{
                public static void main (String args[]){
                    Rectangle rect=new Rectangle();  // 声明对象rect并实例化
                    rect.setWidth(10);            // 调用setter方法设置成员变量
                    rect.setLength(20);
                    rect.display();
                }
            }