Ruby中的Garbarge集合与循环对象引用

前端之家收集整理的这篇文章主要介绍了Ruby中的Garbarge集合与循环对象引用前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我在 Ruby中遇到垃圾收集问题,我认为应该是垃圾回收的对象不是垃圾回收.
require 'ruby-mass'

def find_dependencies(_object_id,_mapped = {})
  mapped = _mapped
  points_to_object = Mass.references(Mass[_object_id])
  ids = points_to_object.keys.map{|x| /\#(\d*)/.match(x).captures.first.to_i}
  mapped[_object_id] = ids

  unmapped = ids - mapped.keys
  unmapped.each do |x|
    new_deps = find_dependencies(x,mapped)
    mapped.merge(new_deps)
  end
  mapped
end

做一些东西,使对象,并找到相关的对象ID. GC.start,然后:

> find_dependencies(144789180)
=> {144789180=>[61895480,144786340,147807540],61895480=>[144789180],144786340=>[144789180],147807540=>[144789180]}

看起来这里有一个循环引用模式,但它们都完全包含在这四个对象中,因此Mark-and-Sweep收集器应该找到它们并将其删除.

所以,我的find_dependencies_function,Mass gem或者Ruby的垃圾收集器中有一个bug.如何缩小这个问题,找出问题所在,解决这个内存泄漏?

解决方法

Ruby中的GC基本上是这样的:

>将所有全局对象标记为活动.
>扫除物体,垃圾收集,除非父母活着.

所以,在循环引用的情况下,A持有到B上的B将得到GC,因为两者都不被实体对象所持有.

根据评论,某些东西一定要保持在某个地方的对象…或者也许Mass是捕获RangeError或某事…

>> a = {}
=> {}
>> a[:a] = a
=> {:a=>{...}}
>> a.object_id
=> 2269556540
>> a = nil
=> nil
>> GC.start
=> nil
>> ObjectSpace._id2ref(2269556540)
RangeError: 0x8746af3c is recycled object
    from (irb):17:in `_id2ref'
    from (irb):17

猜你在找的Ruby相关文章