最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

記一次python 內(nèi)存泄漏問題及解決過程

 更新時間:2018年11月29日 08:21:47   作者:python修行路  
最近工作中慢慢開始用python協(xié)程相關的東西,所以用到了一些相關模塊,如aiohttp, aiomysql, aioredis等,用的過程中也碰到的很多問題,這里整理了一次內(nèi)存泄漏的問題。分享到腳本之家平臺,需要的朋友參考下

最近工作中慢慢開始用python協(xié)程相關的東西,所以用到了一些相關模塊,如aiohttp, aiomysql, aioredis等,用的過程中也碰到的很多問題,這里整理了一次內(nèi)存泄漏的問題

通常我們寫python程序的時候也很少關注內(nèi)存這個問題(當然可能我的能力還有待提升),可能寫c和c++的朋友會更多的考慮這個問題,但是一旦我們的python程序出現(xiàn)了

內(nèi)存泄漏的問題,也將是一件非常麻煩的事情了,而最近的一次代碼中也碰到了這個問題,不過好在最后內(nèi)存溢出不是我代碼的問題,而是所用到的一個包出現(xiàn)了內(nèi)存的問題,下面我通過一個簡單的代碼模擬出內(nèi)存的問題,然后也會將解決的過程描述一下,希望能幫助到遇到同樣問題的朋友。

一、復現(xiàn)問題

其實這次主要是在使用aiohttp寫一個接口的時候出現(xiàn)的問題,其實復現(xiàn)出問題非常容易,我們實現(xiàn)一個簡單的接受post請求接口的服務端,然后實現(xiàn)一個并發(fā)的客戶端來訪問這個接口,來查看內(nèi)存的情況

注意: 這個問題是在一個包的特定版本出現(xiàn)的:multidict==4.5.1,我在整理這個文章2個小時前作者已經(jīng)修復了這個問題發(fā)布了4.5.2版本,已經(jīng)修復了內(nèi)存的問題,并且我也進行了測試驗證

服務端代碼:

from aiohttp import web
async def hello(request):
 return web.json_response(await request.json())
app = web.Application()
app.add_routes([web.post('/', hello)])
web.run_app(app)

客戶端代碼:

import asyncio
import aiohttp
async def foo(times):
 data = {'foo': 1}
 async with aiohttp.ClientSession() as session:
  for x in range(times):
   resp = await session.post('http://localhost:8080', json=data)
   if not x % 100:
    print(await resp.json())
loop = asyncio.get_event_loop()
loop.run_until_complete(foo(100000))
loop.close()

因為我的代碼是在linux上跑的,或者mac上我們都可以通過htop非常方面的實時查看我們程序內(nèi)存的占用情況,我們先將服務端啟動,查看一下我們此時的內(nèi)存情況可以看到占用的

非常少,當我們打開客戶端之后,再次觀察我們可以看到內(nèi)存不斷增長,及時我們客戶端運行完畢內(nèi)存也不會降低。

 當客戶端結(jié)束之后的內(nèi)存:

如果客戶端不停止的話內(nèi)存會一直漲,最后的結(jié)果就是把你的系統(tǒng)內(nèi)存吃完,然后被系統(tǒng)殺掉你的進程。

二、解決內(nèi)存泄漏的過程

像上面的例子是一個非常簡單的程序,不復雜我們也并沒有做上面復雜的操作就是一個簡單的接受post請求的服務端,但是如果是在實際的項目中我們可能會寫非常復雜的業(yè)務邏輯,那到時候我們又如何找到是哪里導致的內(nèi)存問題,當我碰到這個問題的時候,其實我和很多接觸python不久的人差不多,也是不知道怎么查這種問題,各種百度各種查,也找到了好多推薦的工具,memory_profiler庫,objgraph庫,graphviz工具,但是都沒有幫助我迅速的找到問題點在哪里,最后看到標準庫中的tracemalloc,地址:https://docs.python.org/3/library/tracemalloc.html

通過這個包很快幫我找到了內(nèi)存泄漏的地方

接下來按照官網(wǎng)的方法我將代碼進行改寫,來測試到底哪里的問題導致的內(nèi)存泄漏,更改后的服務端代碼為:

from aiohttp import web
import tracemalloc
async def hello(request):
 return web.json_response(await request.json())
async def get_info(request):
 snapshot2 = tracemalloc.take_snapshot()
 top_stats = snapshot2.compare_to(snapshot1, 'lineno')
 print(top_stats)
 return web.Response(text="ok")
if __name__ == '__main__':
 app = web.Application()
 app.add_routes(
  [
   web.post('/', hello),
   web.get("/get_info", get_info)
  ]
 )
 tracemalloc.start()
 snapshot1 = tracemalloc.take_snapshot()
 web.run_app(app)

注意print(top_stats)這行打印的結(jié)果最后要關注

 其實這里就是新增加了一個路由get_info, 我們啟動服務端之后開啟客戶端,當我們客戶端運行完畢之后,可以看到內(nèi)存已經(jīng)漲上去了,并且沒有不會釋放,這個時候,可以直接通過瀏覽器訪問get_info這個路由看看print打印的內(nèi)容,這里將會打印出你程序運行到這個時候那一行的代碼內(nèi)存增長的比較多,進行一次排序,前面的幾個其實都是需要你關注的,因為這里數(shù)據(jù)較多,我就只打印如下前幾個數(shù)據(jù)

<StatisticDiff traceback=<Traceback (<Frame filename='/Users/zhaofan/anaconda3/lib/python3.6/site-packages/aiohttp/web_response.py' lineno=56>,)> size=116500672 (+116500672) count=300004 (+300004)>,
<StatisticDiff traceback=<Traceback (<Frame filename='/Users/zhaofan/anaconda3/lib/python3.6/site-packages/aiohttp/web_response.py' lineno=604>,)> size=11400000 (+11400000) count=200000 (+200000)>, 
<StatisticDiff traceback=<Traceback (<Frame filename='/Users/zhaofan/anaconda3/lib/python3.6/site-packages/aiohttp/web_response.py' lineno=472>,)> size=8000000 (+8000000) count=100000 (+100000)>, 
<StatisticDiff traceback=<Traceback (<Frame filename='/Users/zhaofan/anaconda3/lib/python3.6/site-packages/aiohttp/web_response.py' lineno=353>,)> size=5500000 (+5500000) count=100000 (+100000)>, 
<StatisticDiff traceback=<Traceback (<Frame filename='/Users/zhaofan/anaconda3/lib/python3.6/site-packages/aiohttp/web_response.py' lineno=352>,)> size=5300608 (+5300608) count=100001 (+100001)>,

我們拿第一行來說,我們可以非常清楚的指導web_response的56行代碼導致內(nèi)存增長的最多,當然如果是我們復雜的項目也可以通過類似的方法,這樣就可以非??旖莸恼业轿覀兇a中哪些地方會造成內(nèi)存溢出,便于排查問題,我們點進去看看這行代碼:

我們找到最終行,這個時候我們大致就可以看出哪里的問題了,我們接著看  CIMultiDict

class CIMultiDict(MultiDict):
 def _title(self, key):
  return key.title()

我們可以看到這個它繼承  MultiDict 其實這里我們已經(jīng)應該知道問題就是處在這個MultiDict上了

而這個最終其實最終就是MultiDict這個包,問題出在了這個包上,這個項目是在這里維護的:https://github.com/aio-libs/multidict

查看這個包的時候看到了,果然有人和我遇到了同樣的問題,問題就是出在這里了,已經(jīng)有人提交了bug

https://github.com/aio-libs/multidict/issues/307

不過不得不說國外的程序員真的是熱愛自己的職業(yè),很快這個問題得到了aio-libs小組中人的回應,問題也在我整理這個博客的時候被修復了,在最新的版本:4.5.2中已經(jīng)測試沒有內(nèi)存泄漏的問題

三、總結(jié)

在這里處理的過程中,其實發(fā)現(xiàn)了自己很多的不足,查找問題的方式,以及遇到這種問題的解決思路,不過經(jīng)過這次,至少下次遇到同樣的問題,自己能很快的去查找

以及解決問題,還有就是針對https://docs.python.org/3/library/tracemalloc.html這個庫的使用,也推薦大家多了解一下。

以上所述是小編給大家介紹的記一次python 內(nèi)存泄漏問題及解決過程,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回復大家的。在此也非常感謝大家對腳本之家網(wǎng)站的支持

相關文章

  • pandas dataframe中雙中括號和單中括號的區(qū)別及說明

    pandas dataframe中雙中括號和單中括號的區(qū)別及說明

    這篇文章主要介紹了pandas dataframe中雙中括號和單中括號的區(qū)別及說明,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2023-08-08
  • Python監(jiān)控服務器實用工具psutil使用解析

    Python監(jiān)控服務器實用工具psutil使用解析

    這篇文章主要介紹了Python監(jiān)控服務器實用工具psutil使用解析,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2019-12-12
  • python運算符+條件結(jié)構+循環(huán)結(jié)構

    python運算符+條件結(jié)構+循環(huán)結(jié)構

    這篇文章主要介紹了python運算符、條件結(jié)構、循環(huán)結(jié)構;算術運算符、賦值運算符、邏輯運算符等一些相關內(nèi)容,需要的小伙伴可以參考一下,希望對你的學習有所幫助
    2022-03-03
  • 使用 django orm 寫 exists 條件過濾實例

    使用 django orm 寫 exists 條件過濾實例

    這篇文章主要介紹了使用 django orm 寫 exists 條件過濾實例,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-05-05
  • Python 判斷 有向圖 是否有環(huán)的實例講解

    Python 判斷 有向圖 是否有環(huán)的實例講解

    下面小編就為大家分享一篇Python 判斷 有向圖 是否有環(huán)的實例講解,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2018-02-02
  • django輸出html內(nèi)容的實例

    django輸出html內(nèi)容的實例

    今天小編就為大家分享一篇django輸出html內(nèi)容的實例,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2018-05-05
  • python 如何利用argparse解析命令行參數(shù)

    python 如何利用argparse解析命令行參數(shù)

    這篇文章主要介紹了python 利用argparse解析命令行參數(shù)的步驟,幫助大家更好的理解和學習python,感興趣的朋友可以了解下
    2020-09-09
  • python pandas最常用透視表實現(xiàn)應用案例

    python pandas最常用透視表實現(xiàn)應用案例

    透視表是一種可以對數(shù)據(jù)動態(tài)排布并且分類匯總的表格格式,它在數(shù)據(jù)分析中有著重要的作用和地位,在本文中,我將為你介紹python中如何使用pandas包實現(xiàn)透視表的功能,以及一些常見的應用案例
    2024-01-01
  • Python 異常處理Ⅳ過程圖解

    Python 異常處理Ⅳ過程圖解

    這篇文章主要介紹了Python 異常處理Ⅳ過程圖解,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2019-10-10
  • python中argparse模塊及action='store_true'詳解

    python中argparse模塊及action='store_true'詳解

    argparse?是一個用來解析命令行參數(shù)的?Python?庫,它是?Python?標準庫的一部分,這篇文章主要介紹了python中argparse模塊及action=‘store_true‘詳解,需要的朋友可以參考下
    2023-02-02

最新評論

蒙城县| 舟山市| 南宫市| 安乡县| 岑溪市| 张家川| 宁晋县| 辽中县| 大安市| 鄂托克前旗| 肥城市| 龙山县| 吴堡县| 大关县| 柳江县| 大余县| 玉树县| 南漳县| 永善县| 沧州市| 莱芜市| 广丰县| 巴东县| 若尔盖县| 蒙阴县| 体育| 连平县| 金溪县| 汪清县| 建昌县| 宁国市| 黄骅市| 新乡市| 蕲春县| 邛崃市| 莲花县| 开鲁县| 察哈| 叶城县| 铜川市| 顺义区|