二、读java编程思想五到七章

来源:互联网 发布:新疆知信科技有限公司 编辑:程序博客网 时间:2024/06/05 22:08

1、第五章章有大量关于垃圾回收机制的东西,比较多,参考一篇文章:

https://basebase.github.io/2016/08/27/java-finalize%E6%96%B9%E6%B3%95/

这篇文章讲到对象销毁过程中的几种状态、GC如何追踪这些状态。

2、用构造器进行初始化对象,在java中,”创建“和”初始化“捆绑在一起,两者不能分离。

3、构造器用重载的方式实现,重载的差异在于:参数的个数、参数的类型(不同类型参数的顺序甚至也可以作为区分的标志,但是不要这么做)

重载时会发生类型的一些转换,对于基本数据类型来说,最好匹配他自身,如果没有,那就依次向上匹配吧。byte==>short==>int==>long==>float==>double,其中char比较特殊,在没有char匹配的情况下,优先匹配int,下面的顺序一致。

如果传入的参数较大呢?必须通过类型转换来执行窄化转换,否则编译器报错。

4、构造器:

如果你写的类中没有构造器,编译器自动帮你创建一个默认构造器。

一旦定义了构造器,无论是否有参数,编译器都就不会帮你自动创建默认构造器了。

5、清理:

  • 假设你的对象获得了一块”特殊“的内存区域,由于垃圾回收器只知道释放那些由new分配的内存,所以他不知道该如何释放该对象的这块内存。
  • 为了应对这种情况,java允许在类中定义一个名叫finalize()方法。
  • 工作原理:一旦垃圾回收器准备好释放对象占用的存储空间,将首先调用其finalize()方法,并且在下一次垃圾回收动作发生时,才真正回收对象占用的内存。
  • 注意1:对象可能不被垃圾回收,即垃圾回收这件事不一定会发生
  • 注意2:垃圾回收不等于“析构”
  • 如果垃圾回收这件事一直不发生,那么只有存储空间用完的那一刻,才可能被释放。
  • 注意3:垃圾回收至于内存有关:垃圾回收的唯一目的是为了回收程序不再使用的内存。
  • 如果java虚拟机未面临内存耗尽的情况,他是不会浪费时间去执行垃圾回收以恢复内存的。

6、构造器初始化

static–普通成员初始化—最后是构造器

  • 即使没有显式地使用static关键字,构造器实际上也是静态方法
  • 静态初始化只在Class对象首次加载的时候执行一次

7、枚举

例如:

public enum  ColorLight {    RED(1,"红色"),GREEN(2,"绿色"),YELLOW(3,"黄色");    private int num;    private String color;    ColorLight(int num,String color){        this.num = num;        this.color = color;    }    public int getNum() {        return num;    }    public void setNum(int num) {        this.num = num;    }    public String getColor() {        return color;    }    public void setColor(String color) {        this.color = color;    }}

8、第六章是关于访问权限的,就是private protected 默认 public四种,很基础

9、第七章是复用类:关于组合和继承,主要侧重点不是在如何写,如何写很简单,侧重点在于final关键字修饰变量、方法、类的作用,final是指运行时初始化,不能改变,注意不是编译时期。这就是final定义成静态还是非静态最大的区别。关于继承和初始化的顺序:

首先是父类的静态代码块

然后是子类的静态代码块

开始执行main:

父类的普通方法和构造器

子类的普通方法

子类的构造器

下面用一个程序演示一下:

父类:

public class Insect {    private int i = 9;    protected int j;    Insect(){        System.out.println("i="+i+",j="+j);        j  =39;    }    private static int x1 = printInit("static x1");    static int printInit(String s) {        System.out.println(s);        return 47;    }}

子类:

public class Beetle extends Insect{    private int k = printInit("beetle init");    public Beetle(){        System.out.println("k="+k);        System.out.println("j="+j);    }    private static int x2 = printInit("static x2");    public static void main(String[] args) {        System.out.println("main");        Beetle b = new Beetle();    }}

运行结果,参照我上面说的顺序就一目了然了:

static x1static x2maini=9,j=0beetle initk=47j=39

为了证明:

第一原则:先父类,后子类
第二原则:先执行静态代码块(按顺序执行)、执行普通变量定义、最后是构造器,我将其改造:

public class Insect {    private int i = 9;    protected int j;    private int hhh = printInit("hhh");    static {        System.out.println("我就是想在父类里面输出一下");    }    Insect(){        System.out.println("i="+i+",j="+j);        j  =39;    }    private static int x1 = printInit("static x1");    static {        System.out.println("我也想在父类里面输出一下");    }    static int printInit(String s) {        System.out.println(s);        return 47;    }}
public class Beetle extends Insect{    private int k = printInit("beetle init");    public Beetle(){        System.out.println("k="+k);        System.out.println("j="+j);    }    private static int x2 = printInit("static x2");    public static void main(String[] args) {        System.out.println("main");        Beetle b = new Beetle();    }}

执行结果是:

我就是想在父类里面输出一下static x1我也想在父类里面输出一下   //父类中的静态代码块,按照顺序执行static x2    //子类中的静态代码块main  //mainhhh   //父类中的普通变量或者对象初始化i=9,j=0   //父类中的构造器beetle init  //子类中的普通变量或者对象初始化k=47   //子类中的构造器j=39
原创粉丝点击