V8垃圾回收?看这篇就够了!

什么是内存管理

内存管理是控制和协调应用程序访问电脑内存的过程。这个过程是复杂的,对于我们来说,可以说相当于一个黑匣子。

当咱们的应用程序运行在某个操作系统中的时候,它访问电脑内存(RAM)来达成下列几个功能:

运行需要执行的字节码(代码)

存储程序运行时候所需的数据

加载程序运行所需的运行时环境

上面用来存储程序运行时所需的数据,就是下面要说的堆(heap)和栈(stack)。

栈(stack)

顾名思义,是一种先进后出的结构,参考一下餐盘的取和放。

V8垃圾回收?看这篇就够了!

俄罗斯套娃,我这不禁

V8垃圾回收?看这篇就够了!

栈的特点

由于先进后出性质,在数据的处理上栈有着很好的速度,因为只需从最顶部压栈和出栈就好了,简单明了。

不过,存储在栈中的数据必须是大小有限,生存期确定。

函数执行的时候会创建一个明确的栈,并压入,而当执行期间会存储函数内的所有数据,这就是栈帧。个人感觉可以理解为当前执行函数的快照。

多线程应用程序有多个栈。

栈的操作系统自动分配或释放。

存储在栈中的常见类型有:局部变量(值类型、基本类型、常量)、指针和函数

还记得平常偶尔遇到的stack overflow error吗?这是因为与堆相比,栈的大小受到了限制。大多属语言都是都是这样。

V8垃圾回收?看这篇就够了!

堆(heap)

堆常用来动态内存分配,程序在堆中寻找数据需要使用指针。

堆的特点

效率不如栈,但是可以存储更多的数据

可存储大小不确定的数据,如运行时确定

应用程序中多线程共享堆数据

堆由人工操作,故管理起来很棘手,可能会引起内存泄漏等问题,所以有很多语言有gc机制

存储在堆中的常见类型有:全局变量、引用类型和其他复杂的数据结构

这就是为什么你会遇到out of memory errors这类问题,因为用户的胡乱分配或者未销毁

我们分配给堆的数据其实并没有大小限制,理论上来说你可以分配无穷大的数据。当然如果这样你也得为应用程序分配这么多的内存。 -_-

内存堆栈 与 数据结构堆栈的区别 内存 数据结构
  new一个对象的引用或地址存储在栈区,指向该对象存储在堆区中的真实数据。由程序员分配和回收   是一棵完全二叉树结构  
  存储运行方法的形参、局部变量、返回值。由系统自动分配和回收   是一种连续存储的数据结构,特点是存储的数据先进后出  
内存管理的重要性

与硬盘不同,内存大小有限的,并且往往不是很大。所以说,如果在没有释放无用内存的情况下,无休止的继续消耗内存空间,那么就会造成内存不足甚至操作系统崩溃。。。
所以,以为这种情况,许多语言都提供自动内存管理。并且由于栈是由系统操控,所以我们接下来讨论的自动内存管理主要是堆。

写到这,我想说,我有点不认识堆这个字了。。。

不同的内存管理方法

因为现在语言开发者们不想给使用者增加内存管理的负担(或者说是不相信他们能处理好。。),所以设计出自动管理内存的方式。并且很多语言设计出多种方法去自动管理内存,以供开发者选择。下面一一介绍。

手动内存管理

语言默认不管理内存,比如C、C++,他们提供malloc、realloc、calloc和free等,但是这不是适用于所有人。

GC (Garbage collection)

通过释放无用的内存空间去管理堆内存,gc是当前编程中最常见的一种内存自动管理方法,不过大量处理会造成线程卡主,所以利用碎片时间进行。
使用gc的语言有JVM、JavaScript、C#、Golang、OCaml和ruby。

V8垃圾回收?看这篇就够了!

Mark & Sweep GC

又名: tracing GC。有两个阶段,第一阶段标记那些应该处于活跃状态的数据,下个阶段释放不被引用的数据。
例如JVM、C#、RubyJavaScript和Golang都采用这种方法。
V8引擎还会使用Reference counting GC去弥补,这种gc也可以用于C、C++作为外部库,

Reference counting GC

引用计数内存管理。使用数字代表当前数据是否可回收,数字会根据引用和失去引用而改变,当为0的时候即被回收。但是这种无法处理循环引用。

Resource Acquisition is Initialization (RAII)

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/zyzyxz.html