多态:
多态自始至终都是子类对象在做着变化
【向上转型】类型提升,子类向父类转
【向下转型】强制将父类的引用,转成子类类型
我们能转换的是,父类引用指向了自己的子类对象时,该引用可以被提升(上转),也可以被强制转换(下转)
【成员函数,在多态调用时,编译看左边,运行看右边】
面向接口编程
简单工厂模式
命令模式
6.1 Java8增强的包装类
8种基本数据类型—>包装类
JDK1.5以后提供了自动装箱和自动拆箱功能
借助于包装类,加上自动装箱和自动拆箱功能,开发者可以近似把基本类型变量,近似地当成对象使用;反过来也一样。
1、自动装箱,将y当成是Integer类型
Integer y = new Integer(123);
可以写成
Integer y = 123;
2、自动拆箱,将x当成是int型,与2相加
Integer x = new Integer(123);
x = x + 2;
进行自动拆箱,将x变为int类型,和2进行加法运算;再将和进行自动装箱,赋给x
基本数据类型和String类之间的转换
—->static String.valueOf(xxx)
<—-WrapperClass.parseXxx()或者是包装类的构造器
String intStr = 5+“”; //intStr=“5”
Integer的缓存设计,[-128,127]之间的整数,会被包装成Integer实例,并在一个数组中缓存起来。
所以[-128,127]之间的任一个整数,不管自动装箱多少次,总是引用该数组内同一个元素,故会相等。
超出该范围的Integer实例,系统总是会创建新的实例,所以会出现如下结果:
Integer m = 128;
Integer n = 128;
sop("m==n:"+(m==n)); //false
Integer a = 12;
Integer b = 12;
sop("a==b:"+(a==b)); //true
缓存目的:将一些创建成本高,需要频繁使用的对象缓存起来,提高程序运行效率
6.2处理对象
打印对象p,相当于输出p.toString()结果
toString() 对象的自我描述功能
==和equals()方法
==用来判断两个对象是否相等
基本类型时(不需要数据类型严格相等),只要值相等
引用类型时,必须指向同一个对象
P169常量池:存放编译时就已经确定并保存在.class文件中的一些数据
equals()用于判断引用对象值是否相等,通常需要重写,默认的是比较对象的地址。
String类已经重写,仅比较字符序列
*instanceof运算符 : 用于判断对象的类型。 对象 intanceof 类型(类类型 接口类型)
没有覆写前,Object的equals方法和==运算符的给出结果是相同的
6.7 内部类
外部类有两种作用域:
同一个包内:省略访问控制符,class A{}
任何位置:用public修饰,public class B{}
内部类有四种作用域:
同一个类,同一个包,父子类和任意位置
分别对应private 省略访问控制符 protected public
内部类的文件形式,B是A的内部类,则会生成A.class和A$B.class
外部类成员变量、内部类成员变量与内部类里方法的局部变量同名,则可通过使用this,外部类类名.this作为限定来区分。
通过OutterClass.this.propName的形式访问外部类的实例Field,通过this.propName的形式访问非静态内部类的实例Field
内部类也满足静态关系,即静态成员不能访问非静态成员,不允许在非静态内部类里定义静态成员
非静态内部类
Out.In in = new Out().new In(“测试信息”);
外部类.内部类 变量名 = new 外部类().new 内部类();
静态内部类
使用静态内部类只要把外部类当成静态内部类的包空间即可,较为简单。因此定义一个静态内部类时,优先使用静态内部类
6.7.4 局部内部类 P208
放在方法中定义的叫局部内部类
6.9枚举类
关键字enum
枚举类默认继承java.lang.Enum
枚举类所有实例,必须在第一行显式列出
values方法
枚举类的实例只能是枚举值
枚举类的成员变量,最好都是private final修饰—>所以为了设置成员变量的值,应该有构造器!
java类中定义的接口interface?
6.8 Lambda表达式
主要作用:代替匿名内部类的的繁琐语法 语法糖
() -> {}
Lambda表达式的类型,必须是明确的函数式接口—只能包含一个抽象方法的接口
函数式接口可以包含多个默认方法、类方法,但是只能声明一个抽象方法。
Lamdba表达式的运算结果—>产生一个对象
同样的Lamdba表达式可以被当做是不同的目标类型,唯一的要求是Lambda表达式的形参列表,与函数式接口中唯一抽象方法的参数列表相同
6.10 对象和垃圾回收
垃圾回收只负责回收堆内存中的对象,不会回收任何物理资源。
垃圾回收机制回收对象前,会先调用它的finalize方法,该方法可能使该对象重新复活。
对象在内存中的状态
1可达状态
2可恢复状态 不再有任何引用变量引用该对象,该对象就进入了可恢复状态。将会被调用finalize()
3不可达状态 使用finalize()后仍未使该对象可达,那么该对象将永久性失去引用,进入不可达状态
强制系统进行垃圾回收—>通知系统进行垃圾回收,但是系统是否回收依旧不确定:
System.gc()
RunTime.getRuntime().gc()
java -verbose:gc 类名
- 不要主动调用某个对象的finalize方法,该方法应交给垃圾回收机制调用;
- finalize方法何时被调用,是否被调用具有不确定性,不一定会执行;
- JVM调用finalize方法出现异常时,垃圾回收机制不会报告异常;
- finalize方法,可能使该对象或系统中的其他对象重新可达。
static void runFinalization()
运行处于挂起终止状态的所有对象的终止方法。 强制系统立即调用可恢复对象的finalize方法
对象的软、弱和虚引用
java.lang.ref.Reference
直接已知子类:
PhantomReference, SoftReference, WeakReference
Java.lang.ref 是 Java 类库中比较特殊的一个包,它提供了与 Java 垃圾回收器密切相关的引用类
StrongReference, 强引用 ,最常见的引用方式
SoftReference, 软引用,通过SoftReference类实现,当内存空间足够时,不会被系统回收
WeakReference ,弱引用,通过WeakReference 类实现,引用级别比软引用还低。不管内存空间是否足够,都会被系统回收
PhantomReference ,虚引用,通过PhantomReference 类实现。主要用于跟踪对象被垃圾回收的状态,不能单独使用,必须和引用队列ReferenceQueue联合使用
String str = “ABC”;//该字符串会被放入常量池中管理,使用强引用来管理它 P232
虚引用:
虚引用的主要作用是跟踪对象被垃圾回收的状态,可以通过检查 引用队列中是否已经包含了该虚引用,来了解虚引用所引用的对象是否即将被回收。
为了确保可回收的对象仍然保持原状,虚引用的指示对象不能被获取:虚引用的 get 方法总是返回 null
6.11 修饰符的适用范围
包访问控制符:不用任何修饰符,就是包访问控制符
strictfp关键字:精确浮点运算
native关键字:主要用来修饰一个方法,主要用C实现。
一旦用了这个native方法,该Java程序就失去了跨平台性
6.12 使用JAR文件
Java Archive File
清单文件
*.chm文档 默认用hh.exe打开
CHM是英语“Compiled Help Manual”的简写,即“已编译的帮助文件”。CHM是微软新一代的帮助文件格式,利用HTML作源文,把帮助内容以类似数据库的形式编译储存。
创建可执行JAR包:方法
WAR包 Web Archive File
EAR包 Enterprise Archive File 企业应用文档