Java教程-详解 Java 访问修饰符

Java中有两种修饰符:访问修饰符和非访问修饰符。
Java 中的访问修饰符指定字段、方法、构造函数或类的可访问性或范围。我们可以通过在其上应用访问修饰符来更改字段、构造函数、方法和类的访问级别。
有四种类型的 Java 访问修饰符:
- private: private 修饰符的访问级别仅在类内。它不能从类外访问。
- Default:默认修饰符的访问级别仅在包内。无法从包外访问它。如果您没有指定任何访问级别,它将是默认的。
- Protected : protected 修饰符的访问级别在包内,通过子类在包外。如果您不创建子类,则无法从包外部访问它。
- public:public 修饰符的访问级别无处不在。它可以从类内、类外、包内和包外访问。
非访问修饰符有很多,比如static、abstract、synchronized、native、volatile、transient等,这里只学习访问修饰符。
1)private
private 访问修饰符只能在类中访问。
私有访问修饰符的简单示例
在这个例子中,我们创建了两个类 A 和 Simple。一个类包含私有数据成员和私有方法。我们正在从类外部访问这些私有成员,因此存在编译时错误。
class A{
private int data=40;
private void msg(){System.out.println("Hello java");}
}
public class Simple{
public static void main(String args[]){
A obj=new A();
System.out.println(obj.data); //编译时错误
obj.msg(); //编译时错误
}
}
私有构造函数的作用
如果将任何类构造函数设为私有,则无法从类外部创建该类的实例。例如:
class A{
private A(){}//私有构造函数
void msg(){System.out.println("Hello java");}
}
public class Simple{
public static void main(String args[]){
A obj=new A(); //编译时错误
}
}
注意:除嵌套类外,类不能是私有的或受保护的。
2) Default
如果您没有使用任何修饰符,那么默认情况下将被视为默认修饰符。默认修饰符的访问级别限定在包内部,无法从包外部访问。它提供了比私有修饰符更多的可访问性,但比受保护和公共修饰符更受限制。
示例:默认访问修饰符
在这个例子中,我们创建了两个包:pack和mypack。我们尝试从包外访问A类,但由于A类不是公共的,所以无法从包外访问它。
//通过A.java保存
package pack;
class A{
void msg(){System.out.println("Hello");}
}
//通过B.java保存
package mypack;
import pack.*;
class B{
public static void main(String args[]){
A obj = new A();//编译时错误
obj.msg(); //编译时错误
}
}
在上面的示例中,类 A 及其方法 msg() 的作用域是默认的,因此无法从包外部访问它。
3) Protected
protected 访问修饰符允许在包内外进行访问,但只能通过继承进行访问。
protected 访问修饰符可以应用于数据成员、方法和构造函数,但不能应用于类本身。
它提供了比默认修饰符更多的可访问性。
示例:protected 访问修饰符
在这个例子中,我们创建了两个包:pack 和 mypack。包 pack 中的类 A 是 public 的,所以它可以从包外访问。但是,pack 包中的 msg 方法被声明为 protected,所以只能通过继承的方式从类外访问。
//通过A.java保存
package pack;
public class A{
protected void msg(){System.out.println("Hello");}
}
//通过B.java保存
package mypack;
import pack.*;
class B extends A{
public static void main(String args[]){
B obj = new B();
obj.msg();
}
}
输出:
Hello
4) Public
public 访问修饰符随处可见。它在所有其他修饰符中具有最广泛的范围。
公共访问修饰符示例
//通过A.java保存
package pack;
public class A{
public void msg(){System.out.println("Hello");}
}
//通过B.java保存
package mypack;
import pack.*;
class B{
public static void main(String args[]){
A obj = new A();
obj.msg();
}
}
输出:
Hello
具有方法覆盖的 Java 访问修饰符
如果您正在覆盖任何方法,则被覆盖的方法(即在子类中声明的)不得具有更多限制。
class A{
protected void msg(){System.out.println("Hello java");}
}
public class Simple extends A{
void msg(){System.out.println("Hello java");}//C.T.Error
public static void main(String args[]){
Simple obj=new Simple();
obj.msg();
}
}
default 修饰符比 protected 更具限制性。这就是为什么会出现编译时错误。