(1.1.15)对象成员变量的构造函数和对象构造函数的执顺序以及Static、final、abstract、interface

1-执行顺序优先级优先级:[静态程序块,静态成员】>[非静态程序块,非静态成员]>对象成员变量的构造函数>对象构造函数

变量的优先级>方法的优先级
静态>非静态的
块和成员变量的顺序按照代码的先后顺序

实质是先调用默认构造方法,然后执行隐式的super()或者this回归去父类,此时构造函数的方法体被暂停执行。
然后父类的一切执行完之后,返回子类,先完成代码块和成员变量初始化,再进行构造函数方法体

public class Person {

    public Person(int id) {
        System.out.println("person(" + id + ")");
    }

    public static void main(String[] args) {
        Build b = new Build();
    }
}

class Build {
    Person p1 = new Person(1);

    public Build() {
        System.out.println("this is build's block!");
        Person p2 = new Person(2);
    }

    Person p3 = new Person(3);

}

此处我主要想说明,用构造器创建类和变量的初始化顺序,该程序输出:
person(1)
person(3)
this is build’s block!
person(2)
说明:不论变量放在哪儿,都会先于任意一个方法的执行前执行,包括构造方法,而构造方法是一个类必须会执行的方法,不需要显示的进行调用。同时,不论变量在哪儿分布,只要在方法外部,就一定先于方法初始化。

public class Person {

    public Person(int id) {
        System.out.println("person(" + id + ")");
    }
}

class Build {

    /*静态块*/
    static{
        System.out.println("this is static block!");
    }
    /*非静态块*/
    {
        System.out.println("this is non-static block!");
    }
    static Person p1 = new Person(1);//------------1-----------

    public Build() {
        System.out.println("this is build's block!");
        Person p2 = new Person(2);
    }

    Person p3 = new Person(3);

    public static void main(String[] args) {
        Build b = new Build();
    }
}

this is static block!
person(1)
this is non-static block!
person(3)
this is build’s block!
person(2)

Class A{
 A(){cout<<"A.A Called"}
 A(int i){this(); cout<<"A.A(int) Called"}
}

Class B{
    int i=f();
    int j;
    {
        j=37;
        Cout<<"Block executed"
    }
    B(){
        this(10);
        cout<<"B.B() called"
        }
    B(int i){
    super(i);
    cout<<"B.B(int) called";
        }
    int f(){
    cout<<"B.f() called";
    return 37;
    }
    Static{
        Cout<<" Static Block executed"
    }
}

主函数:
B b=new B();
  1. 调用构造方法B(),执行其中的super()或者this(),不执行真正方法体。 此时需要执行this(10),跳转到B(int i)构造方法中
  2. 调用构造方法B(int i),执行其中的super()或者this(),不执行真正方法体。此时需要执行super(i),跳转到父类的A(int i)构造方法中
  3. 调用构造方法A(int i),执行其中的super()或者this(),不执行真正方法体。此时需要执行this(),跳转到A()构造方法中
  4. 调用构造方法A(),执行其中的super()或者this(),不执行真正方法体。此时没有父类了,预备执行A()方法体之前,执行成员变量和代码块。
  5. A中没有成员变量,该步骤执行完毕
  6. 执行A()的方法体,输出“A.A called”
  7. 执行A(int i)的方法体 ,输出“A.A(int) called”
  8. 回归到子类B中,预备执行构造方法方法体之前,执行成员变量和代码块
  9. [静态]>非静态。输出” Static Block executed”
  10. B.i初始化,输出“”B.f() called””
  11. j初始化
  12. 代码块输出” Block executed”
  13. 执行B(int i)的方法体,输出”B.B(int) called”
  14. 执行B()的方法体,输出”B.B() called”

2-Static的作用

  • Static作用于代码块:
    称作静态代码块(可以初始化static field,不能初始化非static field;初始化只在类装载的时候执行一次。
  • Static作用于methods
    1. Static方法只能访问static 方法,不能访问非static 方法
    2. Static 方法只能访问static field, 不能访问非static field
    3. 非static 方法可以访问static fields 和 static methods
    4. Static method的两种访问方式oject.method class.method, 非static method只有object.method一种访问方式
    5. Static method中不支持this和super
    6. 当一个方法前面的修饰符为private 或 static时,系统会自动在方法前面加一个final,所以该方法可以被继承但不能被重写。
    7. Static 不可以作为局部变量(局部变量包括:函数级局部变量和块级局部变量)
  • Static作用于变量
    • 不在对象的内存中占有空间,而是多个对象共享一个空间。
    • 多个实例对象共享,可以改变
    • 初始化只在类装载的时候执行一次。
    • -

3-final的作用

final类不能被继承,没有子类,final类中的方法默认是final的。
final方法不能被子类的方法覆盖,但可以被继承。
final成员变量表示常量,只能被赋值一次,赋值后值不再改变。java允许将数据成员声明为final,却不赋初值。但是,blank finals必须在使用之前初始化,且必须在构造函数中初始化
final不能用于修饰构造方法。
注意:父类的private成员方法是不能被子类方法覆盖的,因此private类型的方法默认是final类型的。

public class sa {

      final int i; //1、允许

    public sa(int x) {
        this.i=x;    //2、必须有这句话,不然不能编译
    }
    public void doSomething() {
       final int cc;
        System.out.println( i);
       //  System.out.println( cc);  //3、该处会抱错,因为cc未初始化
    }

    }

4-final static的作用

  • 对于变量,表示一旦给值就不可修改,并且通过类名可以访问。
  • 对于方法,表示不可覆盖,并且可以通过类名直接访问。
  • 对于被static和final修饰过的实例常量,实例本身不能再改变了,但对于一些容器类型(比如,ArrayList、HashMap)的实例变量,不可以改变容器变量本身,但可以修改容器中存放的对象,这一点在编程中用到很多。

5-Abstract修饰符

public class B extends A {

    @Override
    void a() {
        System.out.println();
    }

}
abstract class A {

    abstract void a();
    void b(){

    }
}
  1. Abstract class该类不能实例化对象
  2. Abstract class该类可以不包含abstract method,但是只要有一个abstract method那么该类必须为abstract class
  3. Abstract method 该方法没有方法体,需要被override
  4. Abstract class的子类要么实现其父类全部的abstract method,要么也是一个abstract class
  5. Abstract 不能修饰 field
  6. Abstract不能修饰局部变量(方法级局部变量(形参级局部变量,方法体级局部变量)或块级局部变量)

6-interface[java]

声明为interface的类为接口,比抽象类更加抽象的一种机制。在接口中,我们不能提供任何实现,所有方法必须都是抽象的,可以不加abstract关键字,但是编译器对于接口中的方法,都是直接按抽象方法处理的。

7-static全局变量与普通的全局变量有什么区别?static局部变量和普通局部变量有什么区别?static函数与普通函数有什么区别?[C++中]

全局变量本身就是静态存储方式, 静态全局变量当然也是静态存储方式。 这两者在存储方式上并无不同。这两者的区别虽在于非静态全局变量的作用域是整个源程序,当一个源程序由多个源文件组成时,非静态的全局变量在各个源文件中都是有效的。 而静态全局变量则限制了其作用域, 即只在定义该变量的源文件内有效, 在同一源程序的其它源文件中不能使用它。由于静态全局变量的作用域局限于一个源文件内,只能为该源文件内的函数公用, 因此可以避免在其它源文件中引起错误。

static函数与普通函数作用域不同。static函数仅在本文件中使用。只在当前源文件中使用的函数应该说明为内部函数(static),内部函数应该在当前源文件中说明和定义。对于可在当前源文件以外使用的函数,应该在一个头文件中说明,要使用这些函数的源文件要包含这个头文件
static全局变量与普通的全局变量有什么区别:static全局变量只初使化一次,防止在其他文件单元中被引用;
static局部变量和普通局部变量有什么区别:static局部变量只被初始化一次,下一次依据上一次结果值;
static函数与普通函数有什么区别:static函数在内存中只有一份,普通函数在每个被调用中维持一份拷贝

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值