java学习-三个修饰符
三个修饰符
abstract
-
抽象的类:
public class TestAbstract {
public static void main(String[] args) {
Animal aNimal = new Dog();
aNimal.eat();
}
}
abstract class Animal {
public Animal() {}
public void eat() {
System.out.println("动物在吃东西...");
}
public abstract void sleep() {}
}
class Dog extends Animal {
public void eat() {
System.out.println("狗吃骨头...");
}
public void sleep() {
System.out.println("狗在趴着睡觉...");
}
}-
抽象的类不能通过 new的形式创建对象;
-
可被子类继承,继承方式和普通类的继承一样
-
抽象类可以声明为引用,如上面的Animal
-
抽象类中不一定有抽象方法
-
-
抽象方法
public abstract void eat() {}-
抽象方法只声明不实现,所有的实现都放在继承的子类中--比如所有动物都有吃的方法,但每种动物吃的东西不一样,所以Animal只是说明但凡继承这个类的动物都要有吃的方法;
-
抽象方法必须放在抽象类中;
-
子类在继承抽象类后,必须实现其所有的抽象方法,否则子类还是抽象类;如上面的eat方法在子类中的实现:
public void eat() { System.out.println("狗吃骨头..."); }
-
static
静态可以修饰属性和方法
静态成员是全类所有对象共享的成员
不必创建对象,静态成员可以直接通过类名访问的,如下面的count可以直接通过Dog.count访问。类似还有
Arrays.copyOf()等。
-
类的实例属性和静态属性
-
实例属性:通过类new出来的每一个对象各自持有独立的空间,互补影响。
-
静态属性:整个类持有一个共享空间,任何一个对象修改都会影响其他对象。
public class TestStatic {
public static void main(String[] args) {
Dog dog1 = new Dog();
Dog dog2 = new Dog();
dog1.name = "nana";
dog2.name = "nini";
dog1.type = "walking";
dog2.type = "dating";
System.out.println("dog1-name:"+dog1.name); // nana
System.out.println("dog1-type:"+dog1.type); // dating
System.out.println("dog2-name:"+dog2.name); // nini
System.out.println("dog2-type:"+dog2.type); // dating
}
}
class Dog {
String name;
static String type;
}![]()
-
静态属性的应用-计算一个类被创建了对象多少次
class Dog {
String name;
static String type;
static int count;
public Dog() {
this.count ++;
}
}
-
-
局部方法、实例方法和静态方法
class Dog {
public static void eat() {...} // 静态方法
public void sleep() {...} // 实例方法
}-
静态方法允许直接访问静态成员,但不能直接访问非静态成员
-
静态方法内不允许使用this或super关键字(那怎么访问静态属性)
-
静态方法可以被继承,但是不能被重写、没有多态
-
-
静态代码块和动态代码块
class MyClass {
String field = "实例属性1";
static String staticField = "静态属性1";
public MyClass() {
System.out.println("构造方法");
}
{ // 动态代码块
// 给实例属性赋值或者进行一些初始化操作
System.out.println("field: "+ field);
System.out.println("staticField: "+ staticField);
System.out.println("动态代码块");
}
static { // 静态代码块
// 给静态属性赋值或者进行一些初始化操作
System.out.println("staticField: "+ staticField);
System.out.println("静态代码块");
}
}new MyClass();
new MyClass();
// 执行结果如下![]()
-
执行时间:静态属性的初始化和静态代码块只在类被加载时执行一次,此后再也不会执行(且静态代码中不能有非静态属性);动态代码块在每次实例化对象的时候都会执行一次。
-
执行顺序:静态属性>静态代码块>实例属性>动态代码块>构造方法
-
-
带有继承的对象创建过程
class Super {
String field = "父类实例属性";
static String staticField = "父类静态属性";
public Super() {
System.out.println("父类构造方法");
}
{
System.out.println("field: "+ field);
System.out.println("staticField: "+ staticField);
System.out.println("父类动态代码块");
}
static {
System.out.println("staticField: "+ staticField);
System.out.println("父类静态代码块");
}
}
class Sub extends Super {
String field = "子类实例属性";
static String staticField = "子类静态属性";
public Sub() {
System.out.println("子类构造方法");
}
{
System.out.println("field: "+ field);
System.out.println("staticField: "+ staticField);
System.out.println("子类动态代码块");
}
static {
System.out.println("staticField: "+ staticField);
System.out.println("子类静态代码块");
}
}new Sub();
System.out.println("-----------------------");
new Sub();
// 执行结果如下:![]()
-
类加载顺序
![]()
final
-
final修饰类,此类不能被继承。比如:String、Math、System等
-
final修饰方法:此方法不能被修改,既子类不能以覆盖的形式修改
-
final修饰变量:既我们通常意义上的常量。此类常量不再提供默认值,且不能没有值,必须手动赋予初始值。只能被赋值一次。
-
基本类型常量(num):赋值时机:声明变量时/ 声明过后(如下面的:
num = 1) -
引用类型常量(nums): 赋值时机与上相同。不同的是,只要保证引用类型常量指向的堆地址不变即可
-
实例常量(field): 赋值时机: 声明时、动态代码块、构造方法(如果在构造方法内赋值,就必须保证每个构造方法都能被正确赋值)
-
静态常量(staticField):赋值时机:声明时、静态代码块
class TestFinal {
final String field;
public void aVar() {
final int num; // 普通变量
final int[] nums = new int[]{1,2,3};
nums[1] = 4; // 最终指向的地址堆不变,正常运行
nums = new int[]{1}; // 报错,改变了地址
num = 1;
System.out.println(num);
}
} -




浙公网安备 33010602011771号