1.Java源文件被编译器编译成字节码文件。
2. jvm将字节码文件编译成相应的操作系统的机器码。
3.机器码调用相应操作系统的本地方法库执行相应的方法。
虚拟机线程: 虚拟机线程在jvm到达安全点时出现
服务周期线程: 通过定时器调度线程来实现周期性操作的执行
GC线程: GC线程支持JVM中不同的垃圾回收活动
编译器线程: 编译器线程在运行时将字节码动态编译成本地机器码,是jvm跨平台的具体实现
信号分发线程: 接收发送到jvm的信号并并调用jvm方法
线程计数器: 线程私有,无内存溢出问题
虚拟机栈: 线程私有,描述Java方法的执行过程
本地方法区: 线程私有
堆: 运行时数据区,线程共享(创建对象和产生数据都在堆中)
方法区: 线程共享
避免在Java堆和Native堆中来回复制数据带来的资源占用和性能消耗
Eden区: 新创建的对象。内存不足时触发MinorGC进行垃圾回收
ServivorTo区: 保留上一次MinorGC时的幸存者
ServivoreFrom区: 准备再一次GC,利用复制算法
存放长生命周期的对象或大对象。触发的是MajorGC,采用标记清楚算法。
存放Class和Meta(元数据)的信息。GC不会清理。因此会导致class文件过多,会抛出out of memory
Java8优化:讲类的元数据放入本地内存,将常量池和类的静态变量放入Java堆中。
引用计数算法 :
为对象添加引用时加1,删除时减1。计数器为0时回收。互为引用时无法被回收。
可达性分析:
定义一些GC Roots对象,这些对象做为起点向下搜索,如果对象之间没有可达路径,成为不可达,将被回收。
标记清除算法 :
标记所有人对象,清除可回收。效率低。
可被回收小对象多,碎片多,大对象无法使用连续内存。
复制算法 :
不被清除的复制到区域2,然后之间删除所有区域1。效率高,易实现。
同一时刻只能一个内存区域可用,内存空间被压缩到一半。浪费内存。
标记整理算法:
结合前两种算法。标记后移到内存的另一端,然后清除该端对象并释放内存。
分代收集算法 :
新生代,复制算法
老生代,标记清除法
永生代,对象到达15时,被移入
分区收集算法 :
将堆划分成连续的大小不同的小区域,对每个小区域单独处理,灵活使用内存和释放内存。根据系统可接受的系统停顿时间。
一个人对象赋给引用变量。可达性。不会GC。回造成内存泄露
SoftReference类实现。内存空间不足时对象将被回收
WeakReference类实现。垃圾回收过程一定回被回收。
PhantomReference类实现。用于跟踪对象垃圾回收状态
Serial,单线程复制算法:
垃圾回收时需要停止工作线程
复制算法,简单,高效。在Client模式下默认。
ParNew,多线程复制算法:
垃圾回收需要停止工作线程
默认开启和CPU数一样的线程数。可设置。在Server模式下默认的。
Parallel Scavenge,多线程复制算法 :
优化吞吐量,可自适应调节策略。高效利用CPU
三个参数:停顿时间,吞吐大小,自适应是否开启
Serial Old,单线程,标记整理算法 :
生命周期的特点基于标记整理算法。Client模式下默认的。
新生代Serial的未被收集的,到老生代的Serial
Parallel Old,多线程标记整理算法 :
根据生命周期为特点。优先考虑系统吞吐量,其次考虑停顿时间。
新生代Parallel完后,搭配老生代Parallel
CMS,多线程标记清除算法:
目的 :
达到最短的垃圾回收停顿时间,即便在多线程并发下提高系统的稳定性
过程 :
初始标记:只标记和GC Roots直接关联的对象,需暂停所有工作。
并发标记:执行GC Roots跟踪标记过程,不需要暂停
重新标记:垃圾回收过程中改变的,需暂停
并发清除:执行清除,不需暂停
将堆内存划分为大小固定的几个独立区域,跟踪区域GC进度,维护一个优先级列表。
最长时间,最多垃圾。确保在有限时间内获得最高垃圾收集销效率
可精确控制回收效率,不牺牲吞吐量的前提下实现短暂停顿垃圾回收
用户线程发出I/O请求后,内核会检查数据是否就绪,此时用户线程一直阻塞等待内存就绪。
无需阻塞马上返回结果,如果为false,则稍后再发起I/O
selector线程不断轮询多个socket状态
优势 :
Java NIO在用户每个线程都通过selector.select()查询当前通道是否有事件到达,如果没有,则用户线程会一直阻塞。而多路复用复用一个线程管理多个socket通道,触发时才通知用户线程进行I/O读写
非阻塞IO模型在每个用户线程中都进行socket状态检查,而多路复用在系统内核中进行socket状态检查
劣势 :
事件响应体很大时,selector线程会成为瓶颈。实际应用中不建议做复杂逻辑,只做数据的接受和转发。
用户发起IO请求时,系统会为该请求对应的Socket注册一个信号函数。去执行其他的。数据就绪时函数调用IO写操作完成IO请求。
用户线程发起一个asynchronous read操作到内核。
内核返回状态。
内核等待数据准备完成并复制到用户线程。
收到信号即完成。
无阻塞,都在内核中自动完成。
5个类:File,OutputStream,InputStream,Writer,Reader
1个接口:Serializable
阻塞式。
面向流。
Channel通道 : 双向的
Buffer缓冲区 : 容器,数据必须经过,再写到channel上
Selector选择器: 检测channel上是否发生IO,并对IO进行响应和处理。
1对多个channel: 避免线程资料浪费和多线程之间上下文切换开销,提高并发量。
非阻塞式: 面向缓冲区,数据可前后移动,应用于数据的粘包、拆包
1 加载
读取class文件。
在堆中创建class对象。
2 验证
class文件符合当前虚拟机的要求
3 准备
分配内存空间。
设定变量的初始值。
4 解析
jvm会将常量池的符号引用替换为直接引用
5 初始化
通过执行类构造器的client方法为类进行初始化
核心是保障类的唯一性和安全性
动态化模块化系统的一系列规范。
实现热插拔功能
动态发现其他组件的功能,更好的协调工作。
模块化开发的规范。
规范所依赖的服务与架构。