1. 程式人生 > >python_如何在循環引用中管理內存?

python_如何在循環引用中管理內存?

ref don node light port bin 實例對象 highlight object

案例:

  python中通過引用計數來回收垃圾對象,在某些環形數據結構(樹,圖……),存在對象間的循環引用,比如樹的父節點引用子節點,子節點同時引用父節點,此時通過del掉引用父子節點,兩個對象不能被立即釋放

需求:

如何解決此類的內存管理問題?

如何查詢一個對象的引用計數?

import sys

sys.getrefcount(obj)

# 查詢引用計數必多 1 ,因為object也引用 查詢對象

如何解決內存管理問題?

  1. 通過weakref,進行弱引用,當del時候,不再引用,在引用方添加weakref.ref(引用obj),
  2. 使用引用的時候,需要用到函數調用的形式
    #!/usr/bin/python3
    
    import weakref
    import sys
    
    
    class Data(object):
        def __init__(self, value, owner):
            self.value = value
            
            # 聲明弱引用,owner為Node類本身
            self.owner = weakref.ref(owner)
        
        # 通過函數調用的方式訪問引用對象
        def __str__(self):
            return "%s‘s data, value is %s" % (self.owner(), self.value)
        
        def __del__(self):
            print(‘in_data.__del__‘)
    
    
    class Node(object):
        def __init__(self, value):
            
            # 把類本身,也當做參數傳入Data類中
            self.data = Data(value, self)
        
        # 自定義對象名,容易辨認
        def __str__(self):
            return ‘Node‘
        
        def __del__(self):
            print(‘in_node.__del__‘)
        
    
    if __name__ == ‘__main__‘:
        node = Node(100)
        print(node.data)
        
        # 打印node對象的引用計數
        print(sys.getrefcount(node) - 1)
        
        # 當刪除node對象時候,Data實例對象在引用計算為0也相應釋放
        del node
        
        input(‘del done >>>>>‘)
    

      

python_如何在循環引用中管理內存?