python 代碼檢查,實現行級代碼優化

    有時候運行一個python程序,它須要運行很長時間。你或許想提高該程序的運行效率。那該怎麼作那?python

     首先須要你要找到該程序瓶頸在哪裏~   好比,哪一個函數的運行花費時間比較長? 哪一個函數佔用內存比較多,是否須要優化對內存的使用? 哪一個佔用cpu時間比較長? 等...   這些都須要考慮,python有幾個庫能夠幫助你解決這些問題~   廢話很少說,切入主題。ide


首先寫一段讀取一個文件的python腳本:函數

touch c9.py

#!/usr/bin/env python
#Date: 2015/07/21

def read_file(fpath):
    BLOCK_SIZE=1024
    with open(fpath, 'rb') as fd:
        block = fd.read(BLOCK_SIZE)
        if block:
            yield block
        else:
            return

def main():
    for i in read_file('~/access.log')
        print i

if __name__ == "__main__":
    main()

 而後,對該代碼進行測試。測試


首先測試該代碼運行時間:優化

      它是一個外部的python測量。spa

wKiom1Wtq0WjGaA4AAEVu-Nf1Sc199.jpg


real 代表了執行腳本花費的總時間。3d

user 代表了執行腳本花費在cpu的時間。對象

sys 代表了執行腳本花費在內核函數的時間。blog

所以, Real time和user+sys相加的不一樣或許代表了時間花費在等待i/o或者是系統在忙於執行其餘任務。排序


使用cProfile模塊

        若是想知道花費在每一個函數和方法上的時間,以及他們被調用了多少次,你可使用cProfile模塊。

$ python -m cProfile -s cumulative  + 要執行的python腳本    ( -s cumulative 它將經過累積花費在每一個函數上的時間來排序)


wKiom1Wtr_7SVO0dAAQLcFGOoa8346.jpg    

你將看到花費在運行你的腳本總時間是比之前高的,這是咱們測量每一個函數執行時間的損失。


使用line_profile模塊

        line_profile 給出了在你代碼美一行花費cpu時間。

        首先須要安裝line_profiler:

                pip install line_profiler


接下來,你須要制定你想使用裝飾器@profile評估哪一個函數(你不須要把它import 到你的文件中)   wKiom1WtuhSCJLWTAAIfyDyspWo213.jpg

          

接下來測試該代碼:

        $ kernprof -l -v + 要執行的代碼

  wKiom1WtunGjlaE-AARCxdynI2o340.jpg

        -l 標識代表了逐行和-v標識代表詳細輸出。


使用memory_profile模塊

        memory_profile模塊被用於在逐行的基礎上,測量你代碼的內存使用率。儘管如此,它可能使得你的代碼運行的更慢。

        首先安裝memory_profiler

                $pip install memory_profiler

         也建議安裝psutil包,使得memory_profile模塊運行的更快。

                 $ pip install psutil


相似於line_profile的方式,使用裝飾器@profile來標記哪一個函數被跟蹤。


$python -m memory_profiler + 要執行的代碼文件

wKioL1WtvmGiFjWaAAQImIsWaaQ189.jpg


看上面的輸出,注意內存使用率的單位是MiB,這表明的是兆字節(1MiB = 1.05MB).


使用guppy模塊

        使用guppy模塊你能夠跟蹤每一個類型在你代碼中每一個階段(字符、元組、字典等等)有多少對象被建立。


安裝guppy:

$ pip install guppy


而後將你的代碼該改爲以下:

#!/usr/bin/env python
from guppy import hpy

def read_file(fpath):
    hp = hpy()
    print "Heap at the beginning of the function\n", hp.heap()
    BLOCK_SIZE = 1024
    with open(fpath, 'rb') as fd:
        while True:
            block = fd.read(BLOCK_SIZE)
            if block:
                yield block
            else:
                print "Heap at the end of the function\n", hp.heap()
                return

def main():
    hp = hpy()
    print "Heap at the beginning of the function\n", hp.heap()
    for i in read_file('/Users/David/Applications/py/dt'):
        #print i
        pass
    print "Heap at the end of the function\n", hp.heap()

if __name__ == "__main__":
    main()


執行該代碼:

$ python c9.py


wKioL1WtwlWC7D7qAAgVRIuUZSc843.jpg


經過數據結果,能夠看出每一個str、dict、function等對象被建立。


經過以上幾個模塊,能夠更加清晰的瞭解python代碼的執行過程以及對資源的佔用狀況。對代碼優化有很大的幫助~~~ 

相關文章
相關標籤/搜索