python中有自動內存回收機制,一般情況不需要程序員來處理,面試時被大佬問到了,記錄一下。沒有畫圖,推薦讀參考的第一篇博文
gc方式1:引用計數
若此對象無其他對象引用,則立馬回收掉
優點:簡單、實時(將處理垃圾時間分攤到運行代碼時,而不是等到一次回收)
缺點:
1.保存對象引用數會占用一點點內存空間
2.每次執行語句都可能更新引用數,不再使用大的數據結構時,會引起大量對象被回收
3.不能處理循環引用的情況
gc方式2:標記-清除(Mark—Sweep)
此方式主要用來處理循環引用的情況,只有容器對象(list、dict、tuple,instance)才會出現循環引用的情況
循環引用示例:
處理過程
1.將所有容器對象放到一個雙向鏈表中(鏈表為了方便插入刪除),這些對象為0代 2.循環遍歷鏈表,如果被本鏈表內的對象引入,自身的被引用數-1,如果被引用數為0,則觸發引用計數回收條件,被回收掉 3.未被回收的對象,升級為1代
觸發條件:
因為循環引用的原因,並且因為你的程序使用了一些比其他對象存在時間更長的對象,從而被分配對象的計數值與被釋放對象的計數值之間的差異在逐漸增長。一旦這個差異累計超過某個閾值,則Python的收集機制就啟動了,並且觸發上邊所說到的零代算法,釋放“浮動的垃圾”,並且將剩下的對象移動到一代鏈表。
隨着時間的推移,一代鏈表越來越多,多到觸發gc閾值,同樣會對一代鏈表進行標記清除操作,然后將剩下活躍對象升為二代
何時觸發
1.被引用為0時,立即回收當前對象
2.達到了垃圾回收的閾值,觸發標記-清除
3.手動調用gc.collect()
4.Python虛擬機退出的時候