Mono支持内存自动回收,因为MONO集成了内存回收算法。在1.X到2.X的版本中,MONO集成了贝母内存管理及回收算法;而在3.X或更高版本中,则开始启用SGEN内存管理及回收算法。
BOEHM属于一个开源项目,其实现为支持C/C++的内存管理及GC,在C/C++项目中,将分配内存部分接口(malloc或者其他分配内存等接口)替换成BOEHM提供的内存分配接口(GC_malloc),则可以在C/C++项目中实现内存自动管理,无需手动调用free等释放内存接口。而MONO正是基于BOEHM,实现了内存管理及自动GC。
GC实现的方式
引用计数算法:引用技术算法是唯一一种不用用到根集概念的GC算法。其基本思路是为每个对象加一个计数器,计数器记录的是所有指向该对象的引用数量。每次有一个新的引用指向这个对象时,计数器加一;反之,如果指向该对象的引用被置空或指向其它对象,则计数器减一。当计数器的值为0时,则自动删除这个对象。
Mark&Sweep算法:也叫标记清除算法,标记阶段通过标记所有根节点可达的对象,未被标记的对象则表示无引用,可回收,BOEHM正是使用该算法实现内存自动回收; 节点复制算法:将活的节点复制到新内存区,老内存区一次性释放,对象会被转移,应该还需要设置元数据中间层;
贝母算法原理:
BOEHM算法采用标记清除法,在标记阶段通过访问根节点,并遍历到叶子节点,最终将所有存在引用的内存都标记出来,而未标记的内存(所有从堆中分配的内存BOEHM中均有记录,因此可将未标记的部分清除释放掉。
具体如下:
The garbage collector uses a modified mark-sweep algorithm. Conceptually it
operates roughly in four phases, which are performed occasionally as part of
a memory allocation:
垃圾收集器使用了修改后的标记扫描算法。从概念上讲大致分为四个阶段运作,这四个阶段作为内存分配部分被偶尔执行。
Preparation Each object has an associated mark bit. Clear all mark bits, indicating that all objects are potentially unreachable.
起始每个对象都有一个关联的标记位。清除所有标记位,预示所有对象都是潜在无法访问。
Mark phase Marks all objects that can be reachable via chains of pointers from variables. Often the collector has no real information about the location of pointer variables in the heap, so it views all static data areas, stacks and registers as potentially containing pointers.
标记阶段标记所有对象,这些对象可通过指针链表被访问。通常收集器没有指针变量在堆中位置的真实信息,因此它查看所有静态数据区,堆栈和注册器为可能包含指针。
Any bit patterns that represent addresses inside heap objects managed by the collector are viewed as pointers. Unless the client program has made heap object layout information available to the collector, any heap objects found to be reachable from variables are again scanned similarly.
任何位模式被视为指针,位模式代表堆内被收集器管理的对象的地址。除非客户程序已使堆对象布局可供信息收集器使用,否则从所以对象中重复扫描直到找到的所有可访问变量。
Sweep phase Scans the heap for inaccessible, and hence unmarked,objects, and returns them to an appropriate free list for reuse. This is not really a separate phase; even in non incremental mode this is operation is usually performed on demand during an allocation that discovers an empty free list. Thus the sweep phase is very unlikely to touch a page that would not have been touched shortly thereafter anyway.
扫描阶段扫描堆上无法访问的、未标记的、对象,并将其返回给适当的空闲列表以供重用。这并不是一个独立的阶段;甚至在非增量模式下,这是操作通常在分配期间的需求发现一个空的空闲列表。因此扫描阶段极无论如何不可能触及一个此后不久便触及的页面。
Finalization phase Unreachable objects which had been registered for finalization are enqueued for finalization outside the collector.
完成阶段已注册的无法访问的对象最终入队在收集器外部完成。
参考:
https://mp.weixin.qq.com/s?__biz=MzI3NjIwNjA1Ng==&mid=2650438526&idx=1&sn=7d379ccdd16ef10f904c6c75255402a4&chksm=f377c3f9c4004aef0489938829b91c90721c966d17eb219b3ab8ed0fda99534566d1eb232b6b&scene=21#wechat_redirect