Home >Java >javaTutorial >Java access permission control - take you to learn more about the protected keyword (picture)
Inside a class, its members (including members variables Whether a class can be accessed by other classes depends on the modifier of the member; whether a class can be accessed by other classes depends on the modifier of the class. There are four types of class member access permission modifiers in Java: private, none (by default, package access permissions), protected and public, among which only package access permissions and public can modify a class (except inner classes). In particular, many books introducing Java introduce protected in a general way, which often causes misunderstandings. Therefore, this article focuses on revealing the connotation and usage of the protected keyword, and introduces some other modifiers.
Original author of this article: Rico the nerd
Author blog address: http://www.php.cn/
class library referenced by the project. Look at the following example: package java.lang;public class MyObject {
public static void main(String[] args) throws CloneNotSupportedException {
Object o = new Object();
System.out.println(o.hashCode());
}
}
The package name we give our program is java.lang. In fact, we know that java.lang is the package name used by the JDK. The program can be compiled normally, but when we run the program there will be a package conflict warning and throw "java.lang.SecurityException: Prohibited package name: java.lang"
, as shown below shown.CommentsExcept the first sentence of program code, otherwise it cannot be compiled.
2. Overview of Java access rights
Within a class, whether its members (including member variables and member methods) can be accessed by other classes depends on Modifier for this member. There are four types of Java class member access modifiers:private, none (by default, package access), protected and public.
The permissions control is as shown in the following table: members, the two must be distinguished) ,
If you don't want anyone else to have access to the class, you can specify all constructors as private, thereby preventing anyone from creating objects of the class. At this time, objects of this class can only be created within its static members. This situation is a bit like single case mode
, such as the following example:class Test { // private Constructor! private Test() {} // Allow creation via static method: public static Test getTest() { return new Test(); } }
Among the four modifiers mentioned above, except protected, they are all easy to understand and master. We will briefly describe them here: public: Class members modified by public can be directly accessed by all classes; private:被public修饰的类成员只能在定义它的类中被访问,其他类都访问不到。特别地,我们一般建议将成员变量设为private的,并为外界提供 getter/setter 去对成员变量进行访问,这种做法充分体现了Java面向对象的四大特性(封装,多态,继承,抽象)中的封装思想; 包访问权限:包访问权限就是Java中的默认的权限,具有包访问权限的类成员只能被同一包中的类访问。 由于 protected 关键字的真正内涵不太容易理解,我们将在下一节专门介绍 protected 关键字。 很多的有关介绍Java语言的书籍 (包括《Java编程思想》),都对protected介绍的比较的简单,基本都是一句话,就是:被protected修饰的成员对于本包和其子类可见。这种说法有点太过含糊,常常会对大家造成误解。对于protected的成员,要分子类和超类是否在同一个包中两种情况看待,现以 protected方法的调用为例进行说明,protected的成员变量类似。 实质上,protected方法的调用是否合法(编译是否通过)关键是要看被调用的protected方法从根源上看所在的类对应的包与调用代码所在的类对应的包是否相同,若相同,则合法;否则,不合法。当然,无论如何,子类是可以访问继承而来的属于它自己的受保护方法的。 我们可以看下面例子进行了解。 1). 第一种情形:子类与基类不在同一个包中 在上面的示例中,类Father1、Son1 和 Test1 在同一个包p1下,类Son11在包p11下。但是我们知道,无论Son1类还是Son11类,它们的protected方法f()在根源上都来自于p1包中的类Father1,而由于Test1也在p1包中,因此f()方法对Test1类可见,编译通过。但由于Son1类和Son11类中的clone()方法在根源上均来自于java.lang包下的类Object,与 Test1类不在同一包中,因此clone()方法对Test1类不可见,编译不通过。 在上面的示例中,类MyObject2 和 类Test2 分别在包 p2 和 p22 下。因此,在类Test2中通过MyObject2的引用调用MyObject2的protected方法clone()时,由于类MyObject2 和 类Test2 不在同一包中而编译不通过。但是我们知道,虽然 类Test2 的protected方法clone()在根源上也来源于 类MyObject2,但是Test2类作为MyObject2类的子类,是可以访问继承而来的属于它自己的受保护方法的。 在上面的示例中,类MyObject3 和 类Test3 分别在包 p3 和 p33 下。但是由于 MyObject3类的protected方法clone()在根源上来自于类Test3中,而现在正是在Test3类中访问该方法,因此编译通过,原理与示例一类似。 该示例与示例三很类似,唯一不同的是 类MyObject4 重写了从 类Test4 中继承过来的protected方法clone()。这样,MyObject4 的 protected方法clone()在根源上来自于类本身而非Test4类。而类MyObject4 和 类Test4 又不在同一包下,因此编译不通过。 2). 第二种情形:子类与基类在同一个包中 该示例与示例四很类似,唯一不同的是 类MyObject5 与 类Test5在同一个包p5中。正因为二者在同一包中,因此编译通过。 在本示例中,由于类MyObject中的protected方法clone()从根源上来自于Test6类,而现在正是在 Test6 中调用protected方法clone(),因此编译通过。 在本示例中,虽然类MyObject7与Test7类在同一个包p7中,但是由于 类Test7 的protected方法clone()从根源上来自于 java.lang.Object类,而其又与MyObject7不在同一个包中,因此编译不通过。 static:修饰变量和内部类(不能修饰常规类),其中所修饰变量称为类变量或静态变量。静态变量是和类存在一起的,每个实例共享这个静态变量,在类加载时初始化。 final: Variables declared as final must be given an initial value at the time of declaration (of course, except for the blank final case), and the modified variable cannot modify the value. When modifying a class, the class cannot derive subclasses; when modifying a method, the method cannot be overridden by subclasses. If readers want to have a deeper understanding of final, please go to my blog post "Java Inheritance, Polymorphism and Class Reuse". abstract: Modify classes and methods. When modifying a class, the class cannot create objects; when modifying a method, it is an abstract method. As long as a class has an abstract method, the class must be defined as abstract, but an abstract class does not necessarily have to have an abstract method. Within a class, whether its members (including member variables and member methods) can be accessed by other classes depends on the modifier of the member; Whether a class can be accessed by other classes depends on the modifier of the class. There are four types of class member access permission modifiers in Java: private, none (by default, package access permissions), protected and public, among which only package access permissions and public can modify a class (except inner classes). In particular, this article focuses on revealing the connotation and usage of the protected keyword, and introduces some other modifiers. In the process of summarizing this chapter, we have covered a lot of knowledge points, some of which we have specifically mentioned in other blog posts, so we have not made any updates. For more detailed explanation, here is the corresponding link:
三. protected 关键字的真正内涵
//示例一package p1;public class Father1 {
protected void f() {}
// 父类Father1中的protected方法}package p1;
public class Son1 extends Father {}package p11;
public class Son11 extends Father{}package p1;
public class Test1 {
public static void main(String[] args) {
Son1 son1 = new Son1();
son1.f(); // Compile OK,protected方法f()来自于Father1类,与 Test1类 在同一包p1中
son1.clone(); // Compile Error,protected方法clone()来自于Object类,与 Test1类不在同一包中
Son11 son = new Son11();
son11.f(); // Compile OK,虽然Son11类在包p11中,但protected方法f()来自于Father1类,与 Test1类在同一包p1中
son11.clone(); // Compile Error,protected方法clone()来自于Object类,与 Test1类不在同一包中
}
}
//示例二package p2;
class MyObject2 {protected Object clone() throws CloneNotSupportedException {
return super.clone();
}
}package p22;public class Test2 extends MyObject2 {
public static void main(String args[]) {
MyObject2 obj = new MyObject2();
obj.clone(); // Compile Error,protected方法clone()来自于MyObject2类,与 Test2类 不在同一包p1中
Test2 tobj = new Test2();
tobj.clone();// Complie OK,虽然 protected方法clone()来自于MyObject2类,与 Test2类 不在同一包p1中,但Test2类作为MyObject2类的子类,是可以访问继承而来的属于它自己的受保护方法的。
}
}
//示例三package p3;
class MyObject3 extends Test3 {
}package p33;public class Test3 {
public static void main(String args[]) {
MyObject3 obj = new MyObject3();
obj.clone(); // Compile OK,protected方法clone()来自于Test3类,而现在正是在Test3类中访问该方法
}
}
//示例四package p4;
class MyObject4 extends Test4 {
protected Object clone() throws CloneNotSupportedException {
return super.clone();
}
}package p44;public class Test4 {
public static void main(String args[]) {
MyObject4 obj = new MyObject4();
obj.clone(); // Compile Error,protected方法clone()来自于MyObject4类,而Test4类与MyObject4类不在同一个包中
}
}
//示例五package p5;
class MyObject5 { protected Object clone() throws CloneNotSupportedException { return super.clone();
}
}public class Test5 {
public static void main(String[] args) throws CloneNotSupportedException {
MyObject5 obj = new MyObject5();
obj.clone(); // Compile OK,protected方法clone()来自于MyObject5类,而Test5类与MyObject5类又在同一个包中
}
}
//示例六package p6;
class MyObject6 extends Test6{}public class Test6 {
public static void main(String[] args) {
MyObject6 obj = new MyObject6();
obj.clone(); // Compile OK
}
}
//示例七package p7;
class MyObject7 extends Test7 { public static void main(String[] args) {
Test7 test = new Test7();
test.clone(); // Compile Error.
}
}public class Test {}
四. 其他的修饰符
5. Summary
6. Description
The above is the detailed content of Java access permission control - take you to learn more about the protected keyword (picture). For more information, please follow other related articles on the PHP Chinese website!