Java编程思想笔记-类的初始化顺序

1、如果有父类,先初始化父类,然后初始化子类

2、先初始化静态成员变量、静态代码块(static { }包围的代码),然后初始化非静态成员变量、非静态代码块(大括号包围的代码)。静态成员变量间、非静态成员变量间按定义顺序初始化。

3、调用构造函数

class Bowl {
    Bowl(int marker) {
        System.out.println("Bowl(" + marker + ")");
    }

    void f(int marker) {
        System.out.println("f(" + marker + ")");
    }
}

class Cupboard {
    Bowl b3 = new Bowl(3);
    static Bowl b4 = new Bowl(4);

    Cupboard() {
        System.out.println("Cupboard()");
        b4.f(2);
    }

    void f3(int marker) {
        System.out.println("f3(" + marker + ")");
    }

    static Bowl b5 = new Bowl(5);
}

class Table {
    static Bowl b1 = new Bowl(1);

    Table() {
        System.out.println("Table()");
        b2.f(1);
    }

    void f2(int marker) {
        System.out.println("f2(" + marker + ")");
    }

    static Bowl b2 = new Bowl(2);
}

public class Test {

    public static void main(String[] args) throws InterruptedException {

        System.out.println("Creating new Cupboard() in main");
        new Cupboard();
        System.out.println("Creating new Cupboard() in main");
        new Cupboard();
        t2.f2(1);
        t3.f3(1);

    }

    static Table t2 = new Table();
    static Cupboard t3 = new Cupboard();

}

1、开始运行,jvm先加载Test类,此时会初始化静态成员变量  t2、t3

2、然后加载Table类,并初始化该类静态成员变量b1、b2,调用Bowl构造 函数生成对象

3、调用Table构造函数,生成t2对象

4、加载Cupboard类,初始化静态成员变量b4、b5,然后非静态成员变量 b3,并调用Bowl构造函数

5、调用Cupboard构造函数,生成t3对象

6、运行main函数

7、运行 new Cupboard,此时Cupboard已加载入内存,静态成员变量不会再初始化,但非静态成员变量仍然再初始化一次

运行结果:

Bowl(1)
Bowl(2)
Table()
f(1)
Bowl(4)
Bowl(5)
Bowl(3)
Cupboard()
f(2)
Creating new Cupboard() in main
Bowl(3)
Cupboard()
f(2)
Creating new Cupboard() in main
Bowl(3)
Cupboard()
f(2)
f2(1)
f3(1)

  

时间: 2024-08-28 13:02:12

Java编程思想笔记-类的初始化顺序的相关文章

Java编程思想笔记(第二章)

第二章  一切都是对象 尽管Java是基于C++的,但相比之下,Java是一种更纯粹的面向对象程序设计语言. c++和Java都是杂合型语言(hybird language) 用引用(reference)操作对象 类似遥控器(引用)来操作电视(对象) 在Java中你可以创建一个引用,但是没有与任何对象关联,比如: String s; 这个时候如果用则会报错.安全的做法是: 创建一个引用的同时并进行初始化 String s="1111"; 必须由你创建所有对象 New关键字的意思是给我一

java编程思想笔记(第一章)

Alan Kay 第一个定义了面向对象的语言 1.万物皆对象 2.程序是对象的集合,他们彼此通过发送消息来调用对方. 3.每个对象都拥有由其他对象所构成的存储 4.每个对象都拥有其类型(TYpe) 5.某一特定类型的所有对象都可以接收同样的消息. Booch提出一种更简洁的描述: 对象拥有状态(state) 行为(behavior) 和标识(identity) 每个对象都有一个接口 每个对象都属于定义了特性和行为的某个类(特性可以理解为属性的状态,行为可以理解为method) 在面向对象的程序设

Java 编程思想 第五章 ----初始化与清理(1)

从今天开始每天一小时的java 编程思想的阅读和编码,其实就是把书上的代码抄下来. 5.5 清理:终结处理和垃圾回收 初始化和清理工作同等重要,但是清理工作却被常常忘记,但是在使用对象之后,对对象弃之不顾的做法并不是很安全.Java有自己的垃圾回收器负责回收无用的对象占据的内存资源.但也有特殊情况:假定你的内存区域不是用new获得的,这是无法用垃圾回收器释放所以java中允许在类中定义一个名为 finalize()的方法.       工作原理: 一旦垃圾回收器准备好释放对象占用的存储空间,将首

java 编程思想笔记(二)——初始化

一.问题 随着计算机革命的发展,"不安全"的编程方式已逐渐成为编程代价高昂的主因之一. 初始化和清理正是涉及安全的两个问题. 二.java 解决方案 构造器:一种特殊的方法.java 中"初始化"和"创建"捆绑在一起,两者不能分离. 垃圾回收器:释放无用的对象. 三.方法重载 为什么要在这里讲方法重载?我觉得首先:构造器是一种特殊的方法,再一个,构造器除了默认构造器还有有参构造器.为了让方法名称相同而形式参数不同的构造器同时存在,就必须用到方法重

7.JAVA编程思想笔记隐藏实施过程

欢迎转载,转载请标明出处:http://blog.csdn.net/notbaron/article/details/51040237 "进行面向对象的设计时,一项基本的考虑是:如何将发生变化的东西与保持不变的东西分隔开." Java 推出了"访问指示符"的概念,允许库创建者声明哪些东西是客户程序员可以使用的,哪些是不可使用的.这种访问控制的级别在"最大访问"和"最小访问"的范围之间,分别包括:public,"友好的

Java编程思想---第五章 初始化与清理(下)

第五章 初始化与清理(下) 5.7 构造器初始化 可以使用构造器来进行初始化,在运行时可以调用方法或执行某些动作来确定初值,但是我们无法阻止自动初始化的进行,它将在构造器被调用之前发生.例如: public class Counter { int i; Counter() { i = 7; } } 那么i首先被置为0,然后变成7.编译器不会强制你一定要在构造器的某个地方或在使用它们之前对元素进行初始化,因为初始化早已得到了保证. 5.7.1 初始化顺序 在类的内部,变量定义的先后顺序决定了初始化

java 编程思想笔记(三)——类的复用

一:复用功能介绍 复用代码,除了对代码复制并加以改变是不够的,除此之外,还能够使用类而不破坏现有程序代码. java 中代码复用可以分为以下三类:组合,继承,代理. 二:组合 新的类中使用现有类的对象,新的类由现有类的对象组成. 三:继承 通过extends 语法来实现声明. 四:代理 java 对代理没有提供直接支持,但通过组合和继承完成了间接实现,代理是组合和继承的中庸之道.代理=继承+组合 具体理解可以参考相关代码! 五:基类方法被子类重载 子类重载父类的方法,不会屏蔽其在基类中的任何版本

Java编程思想:第5章 初始化与清理

随着计算机革命的发展,“不安全”的编程方式已经逐渐成为编程代价高昂的主因之一. 初始化和清理,正是涉及安全的俩个问题. 5.1 用构造器确保初始化 构造器名与类名相同,没有返回值 5.2 方法重载 构造器的重载与方法重载 5.2.1 区分重载的方法 参数列表的不同(不同顺序也是重载,但不建议这么做) 5.2.2 涉及基本类型的重载 void print(char c){System.out.println("The character is "+c); }    void print(

Java 编程思想 第五章 初始化与清理 上

休整几天,闲了蛋疼也没写文章,这开学了坚持每天写// 必须的天天写.不敢再松懈了.羡慕一好朋友能坚持的静下心来学习. 5.1 用构造器确保初始化 在Java中,通过提供构造器,类的设计者可确保每个对象都会得到初始化.  创建对象时,如果其类具有构造器,Java就会在用户有能力操作兑现之前自动调用相应的构造器,从而保证了初始化的进行.  当然了 接下来的我们需要的问题是: 1.所取的任何名字都可能与类的某个成员名称相冲突: 2.调用股早期是编译器的责任,所以必须让编译器知道应该调用哪个方法: 采取