Mat*_*tty 8 ruby irb object-identity
我注意到对象的ID是以违反直觉的方式分配的.创建对象越早,其对象ID就越大.我原以为他们会按升序分配,而不是相反.
例如:
obj1 = Object.new
obj2 = Object.new
obj3 = Object.new
p obj1.object_id # => 4806560
p obj2.object_id # => 4806540
p obj3.object_id # => 4806520
Run Code Online (Sandbox Code Playgroud)
为什么以这种方式分配它们以及为什么在Ruby解释器运行的代码中有20步而不是1步,但Ruby的irb运行的代码的对象ID之间的区别大得多?
drb*_*ain 14
通过处理许多细节,ruby分配了一大块堆来放置对象:
1 | 2 | 3 | 4 | 5
Run Code Online (Sandbox Code Playgroud)
然后按顺序遍历它们并将它们添加到自由对象的链接列表中.这导致它们在链表上的顺序相反:
freelist ? NULL
freelist ? 1 ? NULL
freelist ? 2 ? 1 ? NULL
freelist ? 3 ? 2 ? 1 ? NULL
freelist ? 4 ? 3 ? 2 ? 1 ? NULL
freelist ? 5 ? 4 ? 3 ? 2 ? 1 ? NULL
Run Code Online (Sandbox Code Playgroud)
分配对象时,ruby使用链表上的第一项:
object = freelist
freelist = object.next_free
Run Code Online (Sandbox Code Playgroud)
所以freelist现在看起来像:
freelist ? 4 ? 3 ? 2 ? 1 ? NULL
Run Code Online (Sandbox Code Playgroud)
并且进一步分配的对象将在小分配中以相反的顺序出现.
当ruby需要分配一大堆堆来存储更多对象时,你会看到object_id跳起来然后再次运行.