在上章中讲解了类文件的生成和包含的信息,但是要加载到jvm中才能启动和运行;
#、一直以为 初始化和实例化 是一个意思,今天就来甑辩一下他们是否相同?
参看:http://www.ibm.com/developerworks/cn/java/j-lo-clobj-init/
http://blog.csdn.net/moreevan/article/details/6968718
开头说到 :类的初始化和对象初始化是 JVM 管理的类型生命周期中非常重要的两个环节,[这里说的是类初始化和对象的初始化,显然这是两个不同的概念,只是他们在大多数情况下是紧密执行的];
一个类的整个生命周期如下:
在装载(loading)阶段,类装载器(Bootstrap ClassLoader 或者自定义的ClassLoader) 把编译形成的class文件载入内存;
连接(lingking)阶段又可以分为三个子步骤:验证(verification)、准备(preparation)和解析(resolution)。
验证阶段 确保java文件数据格式 的正确性,并适于JVM使用。
准备阶段 JVM为静态变量/静态块分配内存空间;
解析过程 就是在class文件的常量池中寻找类、接口、字段和方法的符号引用,当程序运行时需要使用某个符号引用可以再去解析它。
初始化(initialization),初始化的5个启动点:
1.new关键字创建实例(对象实例化会启动初始化过程)
2.反射方法实例化对象(实例化)
3.调用子类时,先初始化父类(可能不会调用其构造方法)
4.初始化主类(主类一般不会实例化)
5.其他指令或句柄如:getstatic、putstatic、invokestatic、REF_getStatic、REF_putStatic、REF_invokeStatic。
注:初始化接口并不需要初始化它的父接口。
所以jvm的启动不会主动进行类初始化,除了主类;
从前4条,可以理解,初始化和实例化是完全不同的概念,今后就不要再混淆了;
静态块 就是常说的 初始化方法:
public class Demos1 { static int a=45; static { System.out.println("i'm static block----"+a); } public static void main(String[] args) { System.out.println("i'm main funtion----"+a); } }} 输出: i'm static block----45 i'm main funtion----45
可以理解为,初始化就是为静态块、静态属性、静态方法分配空间的过程,从类的生命周期图看,他们是先于实例化(构造方法)执行的;
注:静态属性是要先于静态块执行的 储存在静态数据区,静态方法、方法也是在准备阶段存放在method area的;
所以当new一个对象实例的时候,先启动类的初始化过程(静态属性优先静态块执行),而不是先执行构造方法;
class Son{ static{ System.out.println("ok"); } static int a = 34; } public class Demos1 { public static void main(String[] args) { System.out.println(Son.a); } } 输出: ok 34
在这段代码中,调用了Son的属性,这个过程会对Son进行初始化,所以就会先执行Son的初始化过程,后返回; 所以先打印ok而不是34;
注:Son.class不会执行初始化方法;
class Father{ static { System.out.println("父类的初始化方法"); } static int b = 35; } class Son extends Father{ static int a = 34; static{ System.out.println("ok"); } } public class Demos1 { public static void main(String[] args) { System.out.println(Son.b); } } 输出: 父类的初始化方法 35
上段代码,没有输出ok,由于先要对父类进行初始化,先执行b的赋值和打印"父类的初始化方法",完成之后发现b是父类的属性,就不再需要对子类Son初始化了,等以后需要初始化Son时再初始化,如: System.out.println(Son.a);执行Son的初始化方法;
jvm运行时,初始化方法只执行一次,静态属性赋值可以执行多次;
class Father{ static { System.out.println("父类的初始化方法"); } static final int b = 35; } class Son extends Father{ static int a = 34; static{ System.out.println("ok"); } } public class Demos1 { public static void main(String[] args) { System.out.println(Son.b); } } 输出: 35
这段代码连父类的初始化方法都没有执行, 这又是为什么呢?
因为jvm将final声明的常量,放入到NonInitialization类的常量池中去了,它是属于NonInitialization的属性,与Father和Son活生生的脱离了关系,调用Son.b时指向了NonInitialization的这个属性,而不再执行类初始化方法;加上System.out.println(Son.a);可以得到验证:这一步才执行Father的初始化方法;
-XX:+TraceClassLoading
相关推荐
主要是对php初始化对象和析构函数的简单实例进行了介绍,需要的朋友可以过来参考下,希望对大家有所帮助。当对象内部的操作执行完毕的时候,__destruct()被调用, 然后对象所使用的内存被释放出来。
1. 类的创建并实例化 类的定义:在Python中,类通过 class 关键字定义。按照 Python 的编程习惯,类名以大写字母开头,紧接着是(object),表示该类是从哪个类继承下来的。下面是一个简单的类创建并实例化: class ...
spring配置对象实例化后执行的方法,两种实现比对,通过InitializingBean接口,并实现arterPropertiesSet()方法;或者通过applicationContext.xml配置init-method属性
Jmockdta是一款实现模拟JAVA类型或对象的实例化并随机初始化对象的数据的工具框架。单元测试的利器。
对象创建和初始化过程3.1 new对象底层字节码指令分析3.2 对象初始化过程详解【重点】3.2.2 实例变量初始化顺序分析3.2.3 继承中实例变量初始化顺序四 类实例化顺序总结4.1 类初始化阶段4.2 对象的创建和初始化阶段...
# 使用赋值语句定义类属性,记录实例化工具对象的数量 count = 0 def __init__(self, name): self.name = name # 初始化方法内部定义及初始化实例属性 # 类名.类属性名 的方式访问类属性. Tool.count += 1 # 1...
类的初始化顺序,适用于任何一种面向对象的语言。真正了解面向对象的程序的流程。配有实例
5、未用new初始化对象。 6、Session对象为空。 7、对控件赋文本值时,值不存在。 8、使用Request.QueryString()时,所获取的对象不存在,或在值为空时未赋初始值。 9、使用FindControl时,控件不存在却没有做预处理。 10...
NULL 博文链接:https://justcoding.iteye.com/blog/1352346
5、未用new初始化对象。 6、Session对象为空。 7、对控件赋文本值时,值不存在。 8、使用Request.QueryString()时,所获取的对象不存在,或在值为空时未赋初始值。 9、使用FindControl时,控件不存在却没有做预处理。 10...
ts-class-initializable 一个小助手,用于从纯对象启用类实例属性的初始化。 扩展一个Initializable类,您的类构造函数将接受一个普通对象文字作为其第一个参数,并将这些值分配给实例属性。例子class Foo extends ...
类型定义中不一定非要包含完整的类Class和实例instance的定义,如果没有新增的成员,则完全可以从父类型继承过来,qemu-kvm初始化的代码会自动找到父类型并使用父类型的定义。 type的继承关系通过parent指针实现:...
结构体实例(包括共用体)和类实例的初始化方法完全相同,二者都可以应用于继承层次中。不同点是结构体(包括共用体)默认成员为public... ④ 这种初始化对象方式,要求类中不能编写任何构造函数 struct S { //cla
电脑上存储的工作过程中发现的Java代码工具包,既有Swing程序也有工具类!工具类可以节约敲代码数据,有用的直接用就好。
当一个类被加载、连接、初始化后,它的生命周期就开始了,当代表该类的Class对象不再被引用、即已经不可触及的时候,Class对象的生命周期结束。那么该类的方法区内的数据也会被卸载,从而结束该类的生命周期。一个类...
“当用于类类型对象时,初始化的复制形式和直接形式有所不同:直接初始化直接调用与实参匹配的构造函数,复制初始化总是调用复制构造函数。复制初始化首先使用指定构造函数创建一个临时对象,然后用复制构造函数将...
还有以下两个成员函数:一个用于初始化学生姓名、学号、性别和年龄的构造函数,一个用于输出学生信息的函数。编写一个主函数。声明一个学学生对象。然后调用成员函数在屏幕输出学生信息。 编程环境:vs2010,语言:...
可以看出$(…) 实际上返回的是jQuery.fn.init 对象的实例,随后将该对象的prototype 指向了jQuery.prototype (语句jQuery.fn.init.prototype = jQuery.fn),因此产生的实例共享着jQuery.prototype 里的方法和属性且...
主要介绍了c#对象初始化顺序,实例分析了C#对象初始化的相关使用技巧与调用顺序,需要的朋友可以参考下
2.5 类的实例化(定义一个对象) 3 3 防控属性 4 4、构造函数 4 4.1构造函数定义 4 4.2构造函数重载 4 5 初始化列表及其必要性 5 5.1初始化列表 5 5.2初始化列表的必要性 5 6 拷贝构造函数 6 6.1拷贝构造函数概念 6 ...