Java碎片知识(笔记)

  1.在java中有goto,但这只是保留字,并不能使用(const也是)。在eclipse中的报错信息为”Syntax error on token "goto", throw expected“。

goto的类似功能由break/continue 标签实现。

  (1)break 标签

outer:

        for(int i=0; i<10; i++) { if(i == 5) break outer; System.out.print(i + " "); }

  结果:0 1 2 3 4

  分析:break通过标签跳到for循环体外,然后就不会再进入该循环了。

  (2)continue 标签

outer:

        for(int i=0; i<3; i++) { for(int j=11; j<15; j++) { if(j == 13) continue outer; System.out.print(i + " " + j + " "); } }

 

  结果:0 11 0 12 1 11 1 12 2 11 2 12

  分析:continue通过标签跳到for外,但只是跳出当前的这次循环,它会重新进入for循环。

 

  2.是否可以在static环境中访问非static变量?

  eclipse的提示信息:Cannot make a static reference to the non-static field

 

  3.标识符与unicode

  标识符能由字母(unicode),数字,货币符号(¥,$),连接符号(_)组成。

  这里关注unicode,并不是所有unicode都可以作为标识符的一部分。同时,并不是只有数字不能作为标识符首字符。

     int start = 0; int part = 0; for(int i=0x0000; i<=0x10ffff; i++) { if(Character.isJavaIdentifierStart(i)) { start++; // System.out.println(Character.toChars(i));  } if(Character.isJavaIdentifierPart(i)) part++; } System.out.println("Unicode字符集个数:" + (0x10ffff+1)); System.out.println("作为首字符个数:" + start); System.out.println("作为标识符一部分个数:" + part); System.out.println("两者差距:" + (part-start));

  结果:

 

  4.i++与++i

  这两者不只是先加和后加怎么简单,对于i++,其实i是先将自身的值复制给一个临时变量,然后对自身加1(如同++i),最后才参与运算。

     int i = 1; i = i++; System.out.println(i);

  结果: 1

  i++的实现如下所示:

    int temp = i;

    i = i+1;

    return temp;

 

  5.i+++j结果是什么?

        int i = 1, j = 3, result; result = i+++j; System.out.println("result: " + result); System.out.println("i = " + i); System.out.println("j = " + j); 

  结果:

  分析:相当于(i++)+j。编译器会采取贪心规则,尽量找最多的运算符(如果学过编译原理能明白为什么这么做)。

 

  6.float与0

         float f1 = 1f; float f2 = 0f; float f3 = -0f; float result = 0f; result = f1/f2; System.out.println(result); result = f1/f3; System.out.println(result); result = f2/f2; System.out.println(result);

  结果:

  分析:如果是int类型,会抛出异常。

 

  7.运算顺序

  操作数的计算顺序是从左到右的,即使运算符是从右到左。

        int a[] = { 0, 0, 0, 0, 0, 0}; int i = 0; a[++i] = i++; System.out.println(i); System.out.println(Arrays.toString(a));

  结果:

  

        int[] a = { 1, 2, 3 }; int i = 1; a[i] *= i = 2; System.out.println(Arrays.toString(a));

  结果:

  分析:a[i] *= i = 2   ==>   a[i] = a[i] * (i = 2)

 

  8.switch

  switch表达式支持的表达式类型:byte, short, char, int, Byte, Short, Character, Integer, 枚举, String

 

  9.String的最大长度

  String内部是用char[]的,故最大长度就是char[]的最大长度。而char的长度类型最大为int(不能用long),故最大为2147483647。但实际通常不能到这么大,占用的内存太大了(2*2147483647接近4G)。实际能申请的最大值由堆空间的大小来决定。

 

  10.方法重载,重写,隐藏

  (1)重载:只有参数的类型和数目不同。

  (2)重写:子类某个方法重写父类的某个方法。

  (3)隐藏:重写 + static

 

  11.方法重写的条件

  假设sub是子类的方法,super是父类的方法。

  (1)sub和super都是实例方法

  如果都是static则是方法隐藏:

public class test2 {

    public static void main(String[] args) {

        foo c = new coo();

        c.m1();

        c.m2();

    }

}



class foo {

    public void m1() { System.out.println("foo: m1");}

    public static void m2() { System.out.println("foo");}

}



class coo extends foo{

    public void m1() { System.out.println("coo: m1");}

    public static void m2(){ System.out.println("coo");}

}

  结果: coo: m1   foo

  分析:重写的方法能通过RTTI,用的是coo的方法。而加了static后变为方法隐藏,不能通过RTTI,用的是foo的方法。

  (2)sub的签名是super的子签名

   比如void print(List l)是void print(List<Number> l)的子签名。  

  (3)sub的返回类型是super返回类型的可替换类型

  (4)sub的访问权限不能低于super

  (5)sub不能抛出比super更多的异常

 

  12.构造器

    构造器既不是方法也不是成员。

    显式构造器调用语句(this/super)只能在构造器的第一句。

    构造器不能被子类继承,只能显式用super调用。

    是new创建了对象而不是构造器。

    构造器和类的方法中都有一个隐藏的参数this

 

  13.引用类型:

    (1)强引用:没有引用指向该对象时,该对象会被回收。

    (2)弱引用:如果一个对象只有弱引用,每次垃圾回收时都会被回收。

    (3)软引用:如果只有软引用,当JVM内存内存不足就会回收。

    (4)幻影引用:如果只有幻影引用,任何时候都可能被回收

你可能感兴趣的:(java)