返回

Weak的实现(三)剖析对象的引用计数及其引用链

IOS

在深入探讨Weak的实现细节之前,我们必须首先了解对象的引用计数及其引用的链条如何影响对象的生存期。

对象的引用计数

对象的引用计数是一个整数,表示指向该对象的活动引用的数量。当对象被创建时,其引用计数为1。当对该对象创建引用时,引用计数会增加。当对该对象的引用被销毁时,引用计数会减少。

引用链

引用链是对象之间连接的序列。当一个对象引用另一个对象时,就会形成一条引用链。例如,如果对象A引用对象B,对象B引用对象C,那么就会形成一条从对象A到对象C的引用链。

弱引用

弱引用是一种特殊的引用类型,它不会阻止对象被垃圾回收。当对象被销毁时,弱引用将被设置为None。

Weak的实现

Weak的实现使用了一个名为SideTablesMap 的散列表。散列表的键是对象,值是SideTableSideTable 是一个包含有关对象及其引用的信息的数据结构。

SideTablesMap 中的散列函数是:

hash(id(obj)) & (weakref.TABLE_SIZE - 1)

其中:

  • id(obj) 是对象的标识符
  • weakref.TABLE_SIZESideTablesMap 的大小

创建弱引用

当创建一个弱引用时,会发生以下情况:

  1. 为对象创建一个SideTable (如果不存在)。
  2. SideTable 中创建一个WeakRef 对象。
  3. WeakRef 对象添加到SideTablesMap 中。

访问弱引用

当访问弱引用时,会发生以下情况:

  1. SideTablesMap 中获取对象的SideTable
  2. SideTable 中获取WeakRef 对象。
  3. 如果WeakRef 对象为None ,则对象已被垃圾回收。否则,返回WeakRef 对象。

删除弱引用

当删除弱引用时,会发生以下情况:

  1. SideTablesMap 中获取对象的SideTable
  2. SideTable 中删除WeakRef 对象。

示例

以下是一个示例,展示了Weak的实现:

import weakref

class MyClass:
    def __init__(self, name):
        self.name = name

my_object = MyClass('my_object')
weak_reference = weakref.ref(my_object)

print(weak_reference())  # 输出:my_object

# 删除my_object
del my_object

# 访问weak_reference
print(weak_reference())  # 输出:None

在示例中,创建一个名为MyClass的类,并创建一个名为my_objectMyClass实例。然后,使用weakref.ref函数创建my_object的弱引用。

访问弱引用时,它会返回my_object。删除my_object后,再次访问弱引用时,它会返回None

结论

Weak的实现使用散列表SideTablesMap 来跟踪对象及其引用。当创建一个弱引用时,会在SideTablesMap 中创建一个SideTable 和一个WeakRef 对象。当访问弱引用时,它会返回WeakRef 对象。当删除弱引用时,它会从SideTable 中删除WeakRef 对象。