成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

如何排查Python中的內存問題?

譯文
開發 后端
內存問題很難在Python中加以診斷和修復。本文介紹了如何使用流行的開源Python軟件包查明和修復內存泄漏。

[[407502]]

【51CTO.com快譯】發現應用程序內存不足是開發者遇到的糟糕問題之一。內存問題一般很難加以診斷和修復,而在Python中尤為困難。Python的自動垃圾收集讓您易于上手該語言,但出現問題時,開發者不知道如何識別和修復問題。

本文介紹如何診斷和修復開源AutoML庫EvalML中的內存問題。解決內存問題沒什么訣竅,但我希望開發者、尤其是Python開發者可以了解將來遇到這類問題時可利用的工具和優秀實踐。

什么是內存泄漏?

任何編程語言最重要的功能之一是能夠將信息存儲在計算機內存中。每當您的程序創建一個新變量,它都會分配一些內存用于存儲該變量的內容。

內核為程序訪問計算機的CPU、內存和磁盤存儲等資源定義了接口。每種編程語言提供了要求內核分配和釋放內存塊供運行中的程序使用的方法。

程序要求內核留出內存塊供使用,但隨后由于錯誤或崩潰,程序完成使用該內存后從未告訴內核,就會發生內存泄漏。在這種情況下,內核將繼續認為被遺忘的內存塊仍被運行中的程序使用,其他程序無法訪問這些內存塊。

如果運行程序時同樣的泄漏一再發生,被遺忘的內存總量會變得很龐大,因而消耗計算機的大部分內存!在這種情況下,如果程序隨后嘗試請求更多內存,內核會拋出“內存不足”錯誤,程序將停止運行,換句話說“崩潰”。

因此,找到并修復所編寫的程序中的內存泄漏很重要,否則程序最終可能會耗盡內存并崩潰,或者可能導致其他程序崩潰。

第1步:確定是內存問題

應用程序崩潰的原因有很多:也許運行代碼的服務器崩潰了,也許代碼本身存在邏輯錯誤,所以確定眼前的問題是內存問題很重要。

EvalML性能測試悄然崩潰。突然,服務器停止記錄進度,作業悄然停止。服務器日志會顯示編程錯誤引起的任何堆棧追蹤,所以我有預感:崩潰是作業耗用所有的可用內存引起的。

我又重新進行了性能測試,但這次啟用了Python的內存分析器,以獲取內存使用情況圖。測試再次崩潰,當我查看內存圖時,發現了該圖:

圖1.性能測試的內存使用情況

內存使用情況逐漸保持穩定,但隨后達到8 GB!我知道應用服務器有8GB 的內存,所以該圖證實我們耗盡了內存。此外,內存穩定時,我們使用約4 GB的內存,但之前版本的EvalML使用約2 GB的內存。由于某種原因,當前版本使用的內存是平常的大約兩倍。

現在需要找出原因。

第2步:用極簡示例在本地重現內存問題

查明內存問題的原因需要大量實驗和迭代,因為答案通常并不明顯。如果是這樣,您可能不會將其寫入代碼!出于這個原因,我認為用盡可能少的代碼行重現問題很重要。這個極簡示例使您可以在修改代碼時在分析器下快速運行它,查看是否取得進展。

我憑經驗知道,大概在我看到大峰值時,應用程序運行含有150萬行的出租車數據集。我將應用程序精簡至僅運行該數據集的部分。我看到了類似上述的峰值,但這次內存使用量達到了10 GB!

見此情形,我知道有一個足夠好的極簡示例可深入研究。

圖2. 出租車數據集本地重現的內存使用情況

第3步:找到分配最多內存的代碼行

一旦將問題隔離到盡可能小的代碼塊,我們可以看到程序在何處分配最多的內存。這便于您重構代碼和修復問題。

filprofiler是個出色的Python工具。它顯示應用程序中每一行代碼在內存使用高峰時的內存分配情況。這是本地示例的輸出結果:

圖3. fil-profile的輸出

filprofiler根據內存分配情況對應用程序中的代碼行(以及依賴項的代碼)進行排名。線越長越紅,分配的內存越多。

分配最多內存的代碼行用來創建pandas數據幀(pandas/core/algorithms.py和pandas/core/internal/managers.py),數據量達4GB!我在這里截斷了filprofiler的輸出,但它能夠將pandas代碼追溯到用EvalML來創建Pandas數據幀的代碼。

是的,EvalML創建Pandas數據幀,但這些數據幀在整個AutoML算法中都是短暫的,一旦不再使用就應該被釋放。由于實際情況并非如此,加上這些數據幀在內存中的時間足夠長,我認為最新版本帶來了內存泄漏。

第4步:識別泄漏對象

在Python中,泄漏對象是使用完成后沒有被Python的垃圾收集器釋放的對象。由于 Python使用引用計數作為主要的垃圾收集算法之一,這些泄漏對象通常是由對象占有引用時間過長引起的。

這類對象很難找到,但可以用一些Python工具簡化搜尋。第一個工具是垃圾收集器的gc.DEBUG_SAVEALL標志。若設置該標志,垃圾收集器將無法訪問的對象存儲在gc.garbage列表中。這讓您可以進一步研究這些對象。

第二個工具是objgraph庫。一旦對象在gc.garbage列表中,我們可以根據pandas數據幀過濾該列表,并使用objgraph查看哪些其他對象引用這些數據幀、將它們保存在內存中。

這是我在可視化其中一個數據幀后看到的對象圖的一個子集:

圖4. Pandas數據幀使用內存圖,顯示導致內存泄漏的循環引用

這就是我要找的確鑿證據!數據幀通過創建循環引用的PandasTableAccessor對自身進行引用,因此這會將對象保留在內存中,直到Python的垃圾收集器運行并釋放它。(可以通過dict、PandasTableAccessor、dict和_dataframe 追蹤循環。)這對EvalML來說有問題,因為垃圾收集器將這些數據幀保存在內存中的時間太長,以至于我們耗盡內存!

我能夠將PandasTableAccessor追溯到Woodwork庫,并將該問題提交給維護者。他們在新版本中修復后,向pandas存儲庫提交了相關的問題單,這個例子表明了開源生態系統中的合作。

Woodwork更新發布后,我可視化同一個數據幀的對象圖,循環消失了!

圖5.woodwork升級后pandas數據幀的對象圖。不再有循環!

第5步:驗證修復是否有效

我在EvalML中升級Woodwork 版本后,測量了應用程序的內存使用情況。結果發現,內存使用量現在不到過去的一半!

圖6. 修復后性能測試的內存使用情況

原文標題:How to troubleshoot memory problems in Python,作者:Freddy Boulton

【51CTO譯稿,合作站點轉載請注明原文譯者和出處為51CTO.com】

責任編輯:華軒 來源: 51CTO
相關推薦

2018-11-06 12:12:00

MySQL內存排查

2013-03-27 10:32:22

2021-02-26 13:35:46

JavaCPU內存

2024-08-19 00:10:00

C++內存

2015-07-20 10:23:24

NET內存問題排查

2022-07-03 20:31:59

JVMJava虛擬機

2022-01-26 19:42:05

MySQL亂碼排查

2024-01-05 09:23:09

Linux系統內存內存指標

2020-06-23 09:48:09

Python開發內存

2019-12-17 10:01:40

開發技能代碼

2018-08-10 15:00:42

服務器內存排查

2023-10-08 13:10:00

Redis數據庫

2019-01-04 08:00:59

Linux硬件容器

2014-02-27 13:30:26

CacheLinux系統內存不足

2019-04-29 14:23:46

Java服務器CPU

2022-04-11 15:10:34

微服務遷移goroutine

2021-07-30 20:59:21

MySQL內存.參數

2024-11-21 16:47:55

2023-10-13 12:05:55

RedisBig Key

2022-05-13 23:46:52

GO編程內存
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 综合久久亚洲 | 夜夜夜久久 | 一区二区三区日韩 | 欧美不卡在线 | 天天躁日日躁狠狠的躁天龙影院 | 精品1区2区 | 欧美a区 | 免费在线视频精品 | 欧美综合一区二区 | 一级毛片在线播放 | 羞羞视频在线观免费观看 | 久久国产精品免费一区二区三区 | 久久一区二区三区四区 | 亚洲精品乱码久久久久久蜜桃 | 国产一区二区三区 | 欧美日韩国产一区 | 欧美在线视频一区二区 | 欧美日韩一区二区三区四区 | 九久久 | 欧美成人a| 免费黄色大片 | 国产一二区免费视频 | 国产精品av久久久久久久久久 | www免费视频 | 成人国产精品久久久 | 九色在线观看 | 在线高清免费观看视频 | 国产精品久久久久久久久久尿 | 一区二区亚洲 | 特级做a爱片免费69 精品国产鲁一鲁一区二区张丽 | 久久精品国产一区 | 中文字幕乱码一区二区三区 | 欧美福利精品 | 在线观看日本网站 | 久久美国 | 超碰成人免费 | 天天夜夜操| 特级毛片爽www免费版 | 精品欧美激情在线观看 | 99精品视频在线观看免费播放 | 日韩av在线一区 |