v8引擎垃圾回收机制

内存分配

js中存在基本类型和引用类型,两种类型会存储到不同的区域。基本类型的值存储到上下文中,也就是存储在栈内存中;引用类型的值会存储到堆内存中,该内存的地址会存储到栈内存中,按地址引用。

栈中的垃圾回收

栈中数据存储到上下文中,当一个上下文执行完毕后,指向当前执行上下文的指针会下移,表示上层上下文所占内存可被覆盖。有新的上下文时,就可在使用该内存。

堆中的垃圾回收

分区

堆被分为两个区域:新生区、老生区。根据所要存储对象的大小、存活时间存入相应分区。大的对象、存活时间长的对象会存储在老生区,小的对象存储在新生区。新生区和老生区有相同的垃圾回收流程,但使用不同的垃圾回收策略。

垃圾回收流程

  • 标记内存中活动对象和非活动对象。
  • 清理非活动对象所占的内存。
  • 清理后会出现碎片化的内存空间,需对内存做整理。

垃圾回收策略

新生区

  • 新生区容量很小,被均分为两部分,分别为对象区域和空闲区域。
  • 新生区通过副垃圾回收器进行垃圾回收。
  • 新的小对象会被存入对象区域。
  • 对象区域满的时候,进行标记,之后清除垃圾所占内存。
  • 将存活的活动对象赋值到空闲区域,整理碎片化内存。此时,空闲区域和对象区域角色互换。不断进行下去,实现内存的复用。
  • 在新生区中存活时间超过两轮的小对象会被传入老生区存储。

老生区

  • 老生区存储大对象和存活时间长的对象。
  • 老生区通过主垃圾回收器进行垃圾回收,采用标记清除法。
  • 从一组根元素开始递归遍历上下文栈,被引用的为活动对象,否则为非活动对象。
  • 在下次内存清理时清理。
  • 之前的清理方法会产生碎片化内存。可能无法给后续大对象分配连续的内存空间。
    另一种策略—标记整理法可解决该问题。在标记之后,先把活动对象向一端移动,然后清理端边界之外的内存。

你可能感兴趣的:(v8引擎垃圾回收机制)