v8引擎
- V8是一款主流的JavaScript执行引擎
- V8采用即使编译(将源码直接翻译为机器可执行的机器码)
- V8内存设上限(64位 不超过1.5g 32位不超过800M)
V8垃圾回收策略
- 采用分代回收思想
- 内存分为新生代 老生代
- 对不同对象采用不同算法
V8中常用GC算法
- 分代回收
- 空间复制
- 标记清楚
- 标记整理
- 标记增量
V8如何回收新生代
- V8内存空间一分为二
- 小空间用于存储新生代对象(32M|16M)
- 新生代指的是存活时间较短的对象(如函数的局部作用域在函数执行完成后就被释放)
V8内存示意图
新生代对象回收实现
- 回收过程采用复制算法 + 标记整理
- 新生代内存区分为两个等大小的空间
- 使用空间为From,空闲空间为To
- 活动对象存储于From空间
- 标记整理后将活动对象拷贝至To
- From 与 To交换空间完成释放
新生代内存区域被分成两个等大小的区域 From|To,当前使用的是From区域 所有的对象声明都会放在From区域内,当触发Gc机制时 会将当前From内所有的活动对象全都找到,并复制到To内容区域内,拷贝完成后将From和To的空间区域进行交换,From变成To To变成From 完成释放
回收细节说明
- 拷贝过程中可能出现晋升
- 晋升就是将新生代对象移动至老生代
- 一轮GC还存货的新生代需要晋升
- 拷贝过程中To空间的使用率超过25%会将当前活动对象拷贝至老生代
为何To的使用限制是25% 因为 如果占用空间超过限制值之后 From To置换完成后 留给用户存储空间不够用
V8如何回收老生代
老年代对象说明
- 老年代对象存放在右侧老生代区域
- 老年代内容大小 64位操作系统1.4G,32位操作系统700M
- 老生代对象就是指存货时间较长的对象
老年代对象回收实现
- 主要采用标记清除、标记整理、增量标记算法
- 首先使用标记清除完成垃圾空间的回收
- 采用标记整理进行空间优化 (合适采用标记整理,当新生代出现晋升时 新生代内容复制存储到老生代,但是当前老生代内存区域没有完整连续的内存空间进行存储,就会进行标记整理,优化碎片空间)
- 采用增量标记进行效率优化
新老细节对比
- 新生代区域垃圾回收使用空间换时间(等分成两个区域模块,复制交换空间)
- 老生代区域垃圾回收不适合复制算法(老生代存储区域较大,存储内容较多 采用复制算法消耗太大)
增量标记算法优化老生代垃圾回收
将整段的垃圾回收差分成多段交替执行
遍历对象进行标记 标记分为 直接可达和间接可达。
v8总结
- V8是一款主流的JavaScript执行引擎
- V8内存设置上限: v8内存大小 是根据该内存满足应用所需和用户使用体验感知而来
- V8采用基于分代回收思想实现垃圾回收
- V8内存分为新生代和老生代
- V8垃圾回收常见的GC算法