python的內存管理

Python採用了類似Windows內核對象一樣的方式來對內存進行管理。每一個對象,都維護這一個對指向該對對象的引用的計數。如圖所示(圖片來自Python核心編程)

x = 3.14

y = x

 

我們首先創建了一個對象3.14, 然後將這個浮點數對象的引用賦值給x,因爲x是第一個引用,因此,這個浮點數對象的引用計數爲1. 語句y = x創建了一個指向同一個對象的引用別名y,我們發現,並沒有爲Y創建一個新的對象,而是將Y也指向了x指向的浮點數對象,使其引用計數爲2.

我們可以很容易就證明上述的觀點:

 

變量a 和 變量b的id一致(我們可以將id值想象爲C中變量的指針).

我們援引另一個網址的圖片來說明問題:對於C語言來講,我們創建一個變量A時就會爲爲該變量申請一個內存空間,並將變量值 放入該空間中,當將該變量賦給另一變量B時會爲B申請一個新的內存空間,並將變量值放入到B的內存空間中,這也是爲什麼A和B的指針不一致的原因。如圖:

              

 int A = 1                       int A = 2

而Python的情況卻不一樣,實際上,Python的處理方式和Javascript有點類似,如圖所示,變量更像是附在對象上的標籤(和引用的定義類似)。當變量被綁定在一個對象上的時候,該變量的引用計數就是1,(還有另外一些情況也會導致變量引用計數的增加),系統會自動維護這些標籤,並定時掃描,當某標籤的引用計數變爲0的時候,該對就會被回收。

                       

      a = 1                         a = 2                         b = a


# True
a = 1
b = 1
print(a is b)

# True
a = "good"
b = "good"
print(a is b)

# True
a = "very good morning"
b = "very good morning"
print(a is b)

# False
a = []
b = []
print(a is b)

可以看到,由於Python緩存了整數和字符串,因此每個對象只存有一份。比如,所有整數1的引用都指向同一對象。即使使用賦值語句,也只是創造了新的引用,而不是對象本身。長的字符串和其它對象可以有多個相同的對象,可以使用賦值語句創建出新的對象。

#36205432
#36205432
a = {'chen':1,'duo':2}
b = a
print id(a)
print id(b)

#36205432
#36205432
a['chen'] = 5
print id(a)
print id(b)

#42284712
#36205432
a = {'chen':1,'duo':2}
print id(a)
print id(b)
由此可見,當對象本身變化時,引用隨之變化,但內存地址不變。對象有多個引用時,一個引用與對象關係的改變並不影響這個對象的其他引用。


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章