🐵本文继续讲解类和对象相关知识
一、封装
封装就是将对象的属性和实现方法隐藏起来,外部无法获得具体的实现细节,只对外公开接口和对象进行交互,将对象的属性隐藏起来的办法就是用关键字private,被private修饰的成员变量或成员方法只能在当前类中使用
class Student {
private String name; //被private修饰
public int age;
//设置姓名
public void setName(String name) {
this.name = name;
}
//获取姓名
public String getName() {
return this.name;
}
}
public class Test {
public static void main(String[] args) {
Student student = new Student();
student.age = 12; //age是被public修饰的所以可以访问
//student.name = "Sans"; //这样写编译会报错
student.setName("Sans"); //只能使用公开的方法来设置学生对象的姓名
}
}
二、访问限定修饰符
访问限定修饰符包括public、private、protected三种,当它们修饰成员变量和成员方法时会限定对成员变量和成员方法的访问
访问范围 | public | private | 没有修饰符 | protected |
同一包中的同一类 | ✔️ | ✔️ | ✔️ | ✔️ |
同一包中的不同类 | ✔️ | ✔️ | ✔️ | |
不同包中的子类 | ✔️ | ✔️ | ||
不同包中的非子类 | ✔️ |
上面的表格中【不同包中的子类】【不同包中的非子类】【protected】今后会讲,接下来先对包的概念进行讲解
三、包
在Java中有许多类,为了更好的管理这些类就有了包,包在底层就是一个文件夹,文件夹中存在着Java提供给我们的类,同时我们也可以自定义一个包:
包名一般是域名逆置,比如我们可以这样写包名:com.test.www,这样写就会产生com、test、www这三个包,在src的路径下也能看到这三个文件夹,假如在www这个包里创建一个类,在第一行就会通过package关键字显示这个类所在的包的路径:
package com.test.www;
public class Test1 {
}
如果我们没有自己创建包而是在src里直接新建了一个类,在第一行并没有显示包的路径,此时这个类在默认的包中;而当在一个包中创建其它包的类的对象时,则需要进行导包,要用到import关键字
package test1;
import com.test.www.Test1; //导包
public class Num {
public static void main(String[] args) {
Test1 test1 = new Test1(); //在test1包中创建刚刚在www包中创建的Test1类的对象
}
}
之前在使用Scanner从键盘输入数据时也需要导包
import java.util.Scanner; //导包
public class Scan {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
}
}
注意:import无法导入默认包中的类
四、static成员
4.1 static修饰成员变量
被static修饰的成员变量叫做静态成员变量,静态成员变量不属于任何对象,它是所有对象的共同属性
public class Num {
public static int a = 10;
public static void main(String[] args) {
Num num1 = new Num();
Num num2 = new Num();
System.out.println(num1.a); //10
System.out.println(num2.a); //10
}
}
正如刚刚说的,静态成员变量不属于任何对象,所以上述代码的num1.a是不合理的(这样写并不会报错)建议以【类名.】的形式来访问静态成员变量
System.out.println(Num.a);
4.2 static修饰成员方法
被static修饰的成员方法叫做静态成员方法,静态方法也不属于任何对象,它是类的方法;静态方法一般用来访问静态成员变量
class Test {
private static int a = 10; //a同时被private和static修饰
public static int getA() {
return a;
}
}
public class Num {
public static void main(String[] args) {
Test test = new Test();
System.out.println(Test.getA());
}
}
1.在静态方法中不能直接访问非静态成员变量,如果要访问可以创建该成员变量所在类的实例化对象,通过对象来访问成员变量
2. 静态方法中不能有this引用,所以在静态方法内部不能调用非静态方法,因为非静态方法的第一个参数就是this引用
五、代码块
“{}”和“{}”包含的一段代码组成代码块,在Java中代码块有普通代码块、实例代码块和静态代码块
5.1 普通代码块
普通代码块定义在方法内,其使用场景很少
public static void main(String[] args) {
{
int x = 0;
}
int x = 1; //上一个x是定义在普通代码块的局部变量,其作用域只限定在普通代码块内,因此再定义一个x也不会报错
System.out.println(x); //1
}
5.2 构造代码块
构造代码块(也叫实例代码块)定义在类内、方法外,其一般是用来初始化成员变量的,构造代码块在实例化对象时就会被执行
public class Code {
public int x;
public int y;
{
this.x = 1;
this.y = 2;
}
public static void main(String[] args) {
Code code = new Code(); //这条语句执行完后,其对象的x和y就被初始化了
}
}
5.3 静态代码块
被static修饰的代码块称为静态代码块,静态代码块定义在类内、方法外,一般用来初始化静态成员变量
public class Code {
public static int x;
public int y;
static {
x = 1; //这里不能使用this引用,因为静态成员变量不属于任何对象
}
public static void main(String[] args) {
Code code = new Code();
}
}
1. 静态成员变量是属于类的,因此在类被加载时就会被执行,比main方法执行顺序还要高
2. 由于一个类只会被加载一次,所以不管实例化了多少对象静态代码块都只会执行一次
5.4 静态代码块,构造代码块,构造方法的执行顺序
public class Code {
{
System.out.println("构造代码块");
}
static {
System.out.println("静态代码块");
}
public Code() {
System.out.println("构造方法");
}
public static void main(String[] args) {
Code code = new Code();
}
}
静态代码块在类加载时执行,因此最先执行,构造代码块始终优先于构造方法