又读Thinking in Java
前几天又把Thinking in Java的第五章看了一遍,当然。又是收获多多,尽管没有去年第一次看到这本书时的兴奋——当时每天非常晚下班回宿舍后都是必看一点的,可是也捡起了不少忘掉的东西。
本章的标题是:初始化与清理
首先讲述了构造器的由来:在使用对象前,我们都必须确保该对象经过了初始化,那么能够在每一个类中定义一个方法:initialize()(这名字让人想到了非常多设计都用到了名为init()的这种方法),每次我们使用对象前都先调用一下此方法。
那么问题来了:假设我们忘记了调用怎么办呢?出现了问题则必需要有对应的对策来解决,所以人们想到了构造器,让全部需要初始化的工作都在构造器中完毕。那么构造器又是个什么东西呢?作者也没有说,就直接谈到了构造器。
依照我的理解就是:构造器就是一个方法或者说是一个入口,这种方法是用来创建对象的。
然后人们就想办法设计了这种方法(构造器),定义了一些规则:与类同名。无返回值……这里作者提到了一句:new表达式确实返回了对新建对象的引用,可是构造器本身并没有不论什么返回值。这句话能够让人好好想想为什么构造器没有返回值了。
创建对象时:先在内存中分配存储空间,然后调用构造器。
方法重载:Overload。
同一个类中多个方法名同样。但參数列表不同。
重载就是为了偷懒(方便)。
构造器是一个方法,当然也能够重载。
重载的唯一区分方式:独一无二的參数类型列表。
訪问权限、返回值类型、抛出的异常都不能决定该方法是不是重载的。思考个问题:static方法与同名的实例方法是重载的吗?
thiskeyword:
this仅仅能在方法内部使用,表示调用该方法的那个对象。
在构造器中使用this()方法调用其它构造器。
statickeyword:static修饰的属性与方法属于类全部。该类全部对象共享之。
重点来了:清理内存和垃圾回收
创建对象时有一个初始化过程(尽管该过程被构造器所替代了),那么放弃使用该对象时也应该有个与之相应的销毁过程,于是人们为每一个类定义了一个finalize()方法,每次释放该对象所占用的内存空间时先调用该方法然后再清理该内存。
记得学C++时有个析构函数,貌似是类名方法前加个~,每次要自己调用该方法来做清理工作,然后Java为了提高开发者的工作效率,不再这么做了,程序猿不须要自己调用finalize方法。由Java内部的垃圾回收器依据他们自定义的条件去运行。
主要讲垃圾回收器的工作原理:书上也没写个绝对的方法,仅仅是提到了这么几种思路。
1、引用计数法:每一个对象都有一个引用计数器,每次有引用连接到该对象时将计数器加1。当引用断开与该对象的连接时计数器减1,当计数器为0时则将该对象占用的空间释放。
可是有个缺陷,假设有循环引用,即假设A引用了B,而B又引用了A,那么这就成了个死结,推断起来太麻烦,所以这样的方法从未被实现过。
2、自适应的技术:遍历全部的引用,查找活着的对象,然后清理。这也有两种实现的方法:一、停止然后复制(stop-and-copy):就是将全部存活着的对象拷贝到一个新的堆中,然后清理原来的堆,这样要更新全部的引用;二:标记清扫(mark-and-sweep):标记存活的对象,然后将未标记的对象都清理掉,这样会产生非常多碎片空间。两种方法各有利弊。当然要结合起来用咯。
这就涉及到了很多其它操作系统方面的知识。记得学操作系统时也是讲过内存管理的。
再就是提到了一种即时编译器技术JIT(Just-In-Time):为了提高效率,使用时才编译class文件成机器码。
成员初始化也是一个非常重要的点。
写一个过程吧:首先加载.class文件→创建Class的对象,代表该类文件→全部static成员或代码块运行初始化→new一个对象→在堆上分配空间,然后清零该片空间→全部实例变量设置成默认值(8中基本类型+引用类型)→运行字段定义处的初始化动作→运行构造器
数组与可变參数列表
枚举enum
嗯,就这些了吧~
希望有人能好好交流下,每次看完东西认为学到了非常多。可是一段时间不用就忘了。事实上认为当老师是一份不错的工作,时刻滚固着再然后用一下,再然后想一下就会有新东西新想法出来了~事实上不是有非常多成功的人都是当过老师嘛~马云、俞敏洪、李阳……(*^__^*) 嘻嘻……自己YY一下