访问权限修饰符protected和default的区别

访问控制修饰符

对于访问修饰符的作用,种类这里不进行具体描述,关于这方面的东西有太多的参考资料了,放上一张菜鸟教程对各修饰符的说明:

这里需要记录的是上面图片中红圈内protected和default在不同包的子孙类的区别。

protected和default的区别

java中并没有default关键字,当一个方法没有使用任何访问权限修饰符时,就认为该方法使用了默认的修饰符default。而default和protected就只有在不同包子孙类中才会有区别,在其他情况下都是没有区别的。

在A包中创建父类,show方法使用默认修饰符:

1
2
3
4
5
6
public class Father {

void show(){
System.out.println("Father show something");
}
}

在B包中创建子类,test方法中对该子类进行实例化:

1
2
3
4
5
6
class Son extends Father{

public void test(){
Son son = new Son();
son.show(); // 调用父类的show()方法
}

上述代码编译时报错, 提示信息为:

1
2
3
java: 找不到符号
符号: 方法 show()
位置: 类型为B.Son的变量 son

说明被default修饰的父类方法在不同包的子孙类中无法使用。

接下来对protected进行测试,在A包中创建父类,show方法使用protected修饰符:

1
2
3
4
5
6
public class Father {

protected void show(){
System.out.println("Father show something");
}
}

在B包中创建子类,test方法中对该子类进行实例化:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
public class Test{
public static void main(String[] args) {
Son son = new Son();
son.test();

}
}

class Son extends Father{

public void test(){
Son son = new Son();
son.show();
}
}

调用test方法后输出结果为:

1
2
3
Father show something

Process finished with exit code 0

上述结果和菜鸟教程图表描述一致,既在不同包的子孙类中我们是可以调用父类的protected方法的,但是仅限于子类中,如果是在不同包的其他类中实例化子类然后调用父类protected是不可以的,如下所示:

1
2
3
4
5
6
7
8
9
10
11
public class Test{
public static void main(String[] args) {
Son son = new Son();
son.test(); // 这里无法通过编译

}
}

class Son extends Father{

}