对于一个用 python 实现的,长期运行的后台服务进程来说,如果内存持续增长,那么很可能是有了“内存泄露”





一、内存泄露的原因





对于 python 这种支持垃圾回收的语言来说,怎么还会有内存泄露? 概括来说,有以下三种原因:





1、 所用到的用 C 语言开发的底层模块中出现了内存泄露。





2、 代码中用到了全局的 list、 dict 或其它容器,不停的往这些容器中插入对象,而忘记了在使用完之后进行删除回收





3、 代码中有“引用循环”, python 垃圾处理机制无法进行回收





二、 内存泄露的诊断思路





无论是哪种方式的内存泄露,最终表现的形式都是某些 python 对象在不停的增长;因此,首先是要找到这些异常的对象。





 

三、 内存泄露的诊断步骤

 

用到的工具: gc 模块和 objgraph





objgraph 是一个用于诊断内存问题的有用的工具





1、 在服务程序的循环逻辑中,选择出一个诊断点



2、 在诊断点,插入如下诊断语句





import gc  

import objgraph  

### 强制进行垃圾回收  

gc.collect()  

### 打印出对象数目最多的 50 个类型信息  

objgraph.show_most_common_types(limit=50)  

 





3、 检查统计信息,找到异常对象。





运行加入诊断语句的服务程序,并将打印到屏幕上的统计信息重定向到日志中。





运行一段时间后,就可以来分析日志,看看哪些对象在不停的增长。





以我的有问题的程序为例,我将日志记录到 log.txt 中,运行一段时间后,发现 tuple 和 list 类型的对象不停增长:





# grep "^list " log.txt





# grep "^tuple " log.txt



 

由于 tuple 和 list 是一种通用的类型,因此,那些不停增长的 tuple 和 list 到底是什么对象,还是无法得知。我们还得想点办法追踪下去。





如果不停增长的对象,是一些非通用的类型(例如你自己实现的一个 class),那么问题就比较好定位了。





回到我的这个异常程序,为了找出 tuple 和 list 到底是什么? 我采用了排查的方式。由于程序的模块化还不错,我可以每次禁用一个模块,然后重新跑程序,看看在这种情况下, tuple 和 list 是否仍然不停增长。这样,很快就能将故障定位到具体的模块中。

python 内存泄露的诊断的更多相关文章

  1. python 内存泄露的诊断 - 独立思考 - ITeye技术网站

    python 内存泄露的诊断 - 独立思考 - ITeye技术网站 python 内存泄露的诊断 博客分类: 编程语言: Python Python多线程Blog.net  对于一个用 python ...

  2. python内存泄露的诊断(转)

    本篇文章非原创,转载自:http://rstevens.iteye.com/blog/828565 . 对于一个用 python 实现的,长期运行的后台服务进程来说,如果内存持续增长,那么很可能是有了 ...

  3. 记一次调试python内存泄露的问题

    转载:http://www.jianshu.com/p/2d06a1a01cc3 这两天由于公司需要, 自己编写了一个用于接收dicom文件(医学图像文件)的server. 经过各种coding-de ...

  4. 排查python内存泄露中几个工具的使用

    本文主要介绍3个工具:pdb,objgraph,以及pympler. 1.pdb pdb是专门用于python代码调试,模仿gdb. 使用pdb可以查看堆栈,打印变量等. 这里介绍的是命令行下的pdb ...

  5. 关于排查python内存泄露的简单总结

    这次的内存泄露问题是发生在多线程场景下的. 各种工具都试过了,gc,objgraph, pdb,pympler等,仍然没有找到问题所在. pdb感觉用起来很方便,可以调试代码,对原来的代码无侵入性. ...

  6. python内存泄露memory leak排查记录

    问题描述 A服务,是一个检测MGR集群主节点是否发生变化的服务,使用python语言实现的. 针对每个集群,主线程会创建一个子线程,并由子线程去检测.子线程会频繁的创建和销毁. 上线以后,由于经常会有 ...

  7. 使用gc、objgraph干掉python内存泄露与循环引用!

    Python使用引用计数和垃圾回收来做内存管理,前面也写过一遍文章<Python内存优化>,介绍了在python中,如何profile内存使用情况,并做出相应的优化.本文介绍两个更致命的问 ...

  8. python内存泄露诊断过程记录pyrasite

    工具:pyrasite;包含三个命令行 pyrasite / pyrasite-shell / pyrasite-memory-viewer 安装:gdb meliae urwid 说明:Pyrasi ...

  9. python内存泄露查找

    1 前言: 1.1 像Java程序一样,虽然Python本身也有垃圾回收的功能,但是同样也会产生内存泄漏的问题 1.2 在Python程序里,内存泄漏是由于一个长期持有的对象不断的往一个dict或者l ...

随机推荐

  1. CentOS 7 使用 yum 安装 MariaDB 与 MariaDB 的简单配置

    闲置已久的空间环境配置忘得差不多了,今天得空整理,重置了磁盘重新搭建环境,首先安装MariaDB的数据库,在这里记录下安装过程,以便以后查看. 1.安装MariaDB 安装命令 yum -y inst ...

  2. Java常用开源jar包

    转:http://blog.csdn.net/kevingao/article/details/8125683 activation~与javaMail有关的jar包,使用javaMail时应与mai ...

  3. Cesium学习笔记(九):导入3D模型(obj转gltf)

    在用cesium的过程中难免需要导入别人做好的3D模型,这时候就需要将这些模型转成gltf格式了 当然,官方也给了我们一个网页版的转换器,但是毕竟是网页版的,效率极其低下,文件还不能太大,所以我们就需 ...

  4. 6 个 Linux 运维典型问题,大牛的分析解决思路在这里

    作为一名合格的 Linux 运维工程师,一定要有一套清晰.明确的解决故障思路,当问题出现时,才能迅速定位.解决问题,这里给出一个处理问题的一般思路: 重视报错提示信息:每个错误的出现,都是给出错误提示 ...

  5. Ansible 利用playbook批量部署mariadb

    环境说一下 192.168.30.21     ansible 192.168.30.25     client1 192.168.30.26     client2 这里我的ansible环境已经部 ...

  6. PHP 魔术方法浅谈

    php中把以两个下划线(__)开头的方法称之为魔术方法.魔术方法包括: __construct()    类的构造方法  构建方法时被调用 __destruct()      类的析构方法  明确销毁 ...

  7. linu下nginx的安装

    这里用到的环境是nginx-1.8.0,linux用的是CentOS-7-x86_64-DVD-1804.iso版本 1   什么是nginx Nginx ("engine x") ...

  8. Array.prototype.slice.call()的理解

    最近在看廖雪峰的JS课程,浏览器中的操作DOM的那一章,有这样一道题. JavaScript Swift HTML ANSI C CSS DirectX <!-- HTML结构 --> & ...

  9. 终端打印SQL语句

    在 Django 项目的 settings.py 文件中配置: LOGGING = { 'version': 1, 'disable_existing_loggers': False, 'handle ...

  10. Python-----基本操作

    Python是一种简单易学,且功能强大的编程语言.它是面向对象的编程语言. 对象的意义: 对象可以通过一个“.” 的方式来调用这个对象的方法. Python环境安装配置: Python是一种通用的计算 ...