指针:指向某个内存地址的变量。它有两个属性:地址值和指针类型。
空指针:不指向任何内存地址的指针。
指针类型可告诉编译器应该怎样进行接下来的数据访问。int类型和float类型就不是一样的。举个例,如:Cat cat = null;就告诉了cat变量是cat类型,则编译器会让cat变量去访问Cat类型数据;也即相当于在声明变量时完成了Cat类型的初始化,所以即使是Cat cat = null;这种情况,cat变量也能访问到到Cat类的静态成员,而不会报空指针,如果去访问Cat类的普通成员,则会报空指针,因为普通成员必须要在new之后才存在于堆内存中的。所以,我们可以说null是一个只有类成员的对象(万物皆对象)。
还有一个解释:在Java里,对象调用类成员时,实际上是委托类本身来调用的,所以null对象能调用类成员而不报空指针。基本数据类型用”==”判断值是否相等
两个引用变量用”==”判断引用变量存的地址值是否相等,”==”不能用于比较类型上没有父子关系的两个对象,那样会报错。
equals()方法是Object类的方法,它规定与自身作比较才相等(即两个对引用变量指向的是同一个对象才相等)。可通过重写它自定义相等规则。如引用类型String类的equals()方法就是重写Object类的equals方法,它的规定是:只要内容相等或是与对象本身作比较就相等。
Java用常量池管理曾经用过的字符串,执行String str = “java”; 时,常量池就会缓存一个”java”,若再执行String s =”java”;则系统会直接让s指向之前缓存的java,所以str与s共用一个对象,因此str == s 的结果为true;关于final
- final修饰的成员变量必须显示赋值,不然该成员变量失去了存在的意义。
- final修饰的类变量,要么在静态块中赋值,要么在声明时就赋值。
- final修饰的实例变量,要么在普通初始化块和构造器中赋值,要么在声时就赋值。
- final修饰的类不可被继承,修饰的方法不可被重写,但可被重载。
- 宏变量:被final修饰且在定义时就赋好初值的变量。编译时,会将所有用到宏变量的的地方都直接替换成该变量的值。示例:
//1.声明非宏变量
String a = "ja";
String b = "va";
System.out.print(a+b == "java");//结果为false
//2.声明宏变量
final String a = "ja";
final String b = "va";
System.out.print(a+b == "java");//结果为true
//这里的a、b是宏变量,所以会直接替换成它的值,所以此时的a+b直接就是"java"。
关于抽象类
1. 抽象类不能被实例化,主要用于被继承;抽象方法主要用被重写。抽象类示例:public abstract class A{}
2. static与abstract不能同时修饰方法,但可同时修饰内部类。关于接口
1. 与抽象类和普通类的单继承多实现不同,接口可多继承多实现。
2. 接口体现的是规范与实现相分离的设计哲学,抽象类体现的是一处模板式设计。
3. 接口不能包含初始化块、构造器、普通成员变量、普通方法,而抽象类均可包含,且能全是普能方法。
4. 接口的所有成员都用public 修饰。
5. 接口的成员变量必须用public static final 修饰,不指定时默认是它们。
6. 接口中的方法必须是public abstract 修饰, 不指定时默认是它们。内部类
如何使用:Out.Int in = new Out().new Int(); //in就代表内部类Int的实例对象。
匿名内部类
- 如果一个接口的实现类须使用多次,则定义成独立类,但只使用一次时,则应该定义成匿名内部类。
- 匿名内部类里不能定义构造器,但可以定义初始化块来完成需要构造器完成的事。
- 匿名内部类格式:new 接口(或类){ 重写 },只需要重写一次某个类的方法时,可使用匿名类内部类。
- 匿名内部类访问的外部局变量默认是final修饰的。
缓存原理
需要重复访问的数据,如果在数据库或硬盘等外部系统中,则访问获取时会很慢,如果把这些数据缓存到内存里,每次获取先看缓存里有没有,有就直接取,没有就从外部系统中获取后放到缓存里,以供下次直接从缓存里取。
注:如果Integer采用Integer.valueOf(99)
创建对象,则会缓存该对象,即99会放进缓存里。Integer只缓存 -128~127之间的对象。