python的内存管理机制(zz)

本文转载自:http://www.cnblogs.com/CBDoctor/p/3781078.htmlhtml

先从较浅的层面来讲,Python的内存管理机制能够从三个方面来说python

(1)垃圾回收编程

(2)引用计数函数

(3)内存池机制性能

1、垃圾回收:spa

python不像C++,Java等语言同样,他们能够不用事先声明变量类型而直接对变量进行赋值。对Python语言来说,对象的类型和内存都是在运行时肯定的。这也是为何咱们称Python语言为动态类型的缘由(这里咱们把动态类型能够简单的归结为对变量内存地址的分配是在运行时自动判断变量类型并对变量进行赋值)。操作系统

2、引用计数:设计

Python采用了相似Windows内核对象同样的方式来对内存进行管理。每个对象,都维护这一个对指向该对对象的引用的计数。如图所示(图片来自Python核心编程)3d

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

 

 3、内存池机制

 

Python的内存机制以金字塔行,-1,-2层主要有操做系统进行操做,

  第0层是C中的malloc,free等内存分配和释放函数进行操做;

  第1层和第2层是内存池,有Python的接口函数PyMem_Malloc函数实现,当对象小于256K时有该层直接分配内存;

  第3层是最上层,也就是咱们对Python对象的直接操做;

在 C 中若是频繁的调用 malloc 与 free 时,是会产生性能问题的.再加上频繁的分配与释放小块的内存会产生内存碎片. Python 在这里主要干的工做有:

  若是请求分配的内存在1~256字节之间就使用本身的内存管理系统,不然直接使用 malloc.

  这里仍是会调用 malloc 分配内存,但每次会分配一块大小为256k的大块内存.

  经由内存池登记的内存到最后仍是会回收到内存池,并不会调用 C 的 free 释放掉.以便下次使用.对于简单的Python对象,例如数值、字符串,元组(tuple不容许被更改)采用的是复制的方式(深拷贝?),也就是说当将另外一个变量B赋值给变量A时,虽然A和B的内存空间仍然相同,但当A的值发生变化时,会从新给A分配空间,A和B的地址变得再也不相同

a=(1,2,3,4,5)
b=a
print(id(a))
print(id(b))

a=(1,2,3)
print(a)
print(b)
print(id(a))
print(id(b))

而对于像字典(dict),列表(List)等,改变一个就会引发另外一个的改变,也称之为浅拷贝

 

 

 

附:

引用计数增长

1.对象被建立:x=4

2.另外的别人被建立:y=x

3.被做为参数传递给函数:foo(x)

4.做为容器对象的一个元素:a=[1,x,'33']

引用计数减小

1.一个本地引用离开了它的做用域。好比上面的foo(x)函数结束时,x指向的对象引用减1。

2.对象的别名被显式的销毁:del x ;或者del y

3.对象的一个别名被赋值给其余对象:x=789

4.对象从一个窗口对象中移除:myList.remove(x)

5.窗口对象自己被销毁:del myList,或者窗口对象自己离开了做用域。

 

垃圾回收

一、当内存中有再也不使用的部分时,垃圾收集器就会把他们清理掉。它会去检查那些引用计数为0的对象,而后清除其在内存的空间。固然除了引用计数为0的会被清除,还有一种状况也会被垃圾收集器清掉:当两个对象相互引用时,他们自己其余的引用已经为0了。

二、垃圾回收机制还有一个循环垃圾回收器, 确保释放循环引用对象(a引用b, b引用a, 致使其引用计数永远不为0)。

 

参考:

[1] Python 2.7.8 documentation memory management

[2]深刻详解python传值问题及内存管理机制-CSDN

[3]Python内存池管理与缓冲池设计 - 张知临的专栏

[4]理解python变量和内存管理 

相关文章
相关标签/搜索