前言:
我们平时做项目或是学习的时候,访问修饰符用的最多的就是 public 和 private 两种,对于这两种访问修饰符,稍有编程经验的人都比较熟悉。但是另外两种呢?protected 和 default 用的比较少,因此很多人对这两种访问修饰符的了解很模糊。可能很多人只记得下面这张图,但是对访问修饰符的关键作用“访问控制”理解的还不够深刻。
今天在温故而知新的时候,对 protected 这个访问修饰符有了一点儿新的理解,趁热打铁,就写出来分享分享。
简单叙述四种访问修饰符的区别:
public:
在当前类中,凡是用public修饰的方法(类方法、实例方法),都可被其它类访问(这个类可以在任何地方,同不同包无所谓)。同理,public修饰的属性亦如此。
private:
在当前类中,凡是用private修饰的方法(类方法、实例方法),都是私有的,有且仅有该类自己可以访问。属性同理。
default:
使用default修饰的方法(类方法、实例方法),只可被“当前包中的类”访问,其它包中的类无权访问。属性同理。
protected:
使用protected修饰的方法,在default的基础上,还可被子孙类(直接子类、间接子类)访问。属性同理。
关于protected的一点儿新发现:
父类:
package parent_package;
public class Parent {
protected static void proStaMethod() {
}
protected void proMethod() {
}
}
子类:
package child_package;
import parent_package.Parent;
public class Child extends Parent {
public void test() {
// 类名访问
Parent.proStaMethod();
// 对象访问
Parent parent = new Parent();
parent.proStaMethod();
// this访问
this.proStaMethod();
this.proMethod();
// super访问
super.proStaMethod();
super.proMethod();
}
}
我把子类访问父类 protected 方法的所有途径都列出来了,有一个地方非常有意思:
“对象访问”的时候只能访问到 Parent 类受保护的”类方法“ proStaMethod() ,并不能访问到受保护的”实例方法“ proMethod() 。
有没有人对此感到惊讶呢?如果按我们一开始的说法,子类中是可以访问到父类中受保护的实例方法的。在这里,为什么“ this 访问”和“ super 访问”都可以访问到实例方法,唯独“对象访问”的形式不行呢?
我的解释:
类比现实生活,我们拜访别人的时候,有两种途径:私下拜访、公开拜访。私下拜访就会有人情在里面;公开拜访就更倾向于公开平等,私人关系就摆在了次要的位置上。
“ this 访问”和“ super 访问”就好比是私下拜访:子类私下拜访父类,就明显的体现出“父子关系”,父类和子类处于不同的包,按理说,父类对子类所在的包是排斥的,但是由于“亲情”,父类让子类继承了自己保护的方法(相当于从父类那里 copy 一份),并且还让子类有权访问自己保护的方法,“ this 访问”就是子类访问继承自父类的方法(已经是自己的了),“ super 访问”就是去父类那里,访问属于父类的方法。
”类名访问“和”对象访问“就好比公开拜访:这时候,”父子关系“就要抛开,公开平等的规则最重要!既然父类对子类在所的包是排斥的,那么,父类到子类这儿来了以后,父类保护的方法肯定是谁都不让访问的(包括子类)。这也就解释了子类为什么不能通过”对象访问“的形式访问父类的保护方法了。