<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          監(jiān)控 Python 內(nèi)存使用情況和代碼執(zhí)行時間!

          共 5002字,需瀏覽 11分鐘

           ·

          2023-02-13 18:39

          來源:網(wǎng)絡

          我的代碼的哪些部分運行時間最長、內(nèi)存最多?我怎樣才能找到需要改進的地方?”

          在開發(fā)過程中,我很確定我們大多數(shù)人都會想知道這一點,在本文中總結(jié)了一些方法來監(jiān)控 Python 代碼的時間和內(nèi)存使用情況。

          本文將介紹4種方法,前3種方法提供時間信息,第4個方法可以獲得內(nèi)存使用情況。

          • time 模塊

          • %%time 魔法命令

          • line_profiler

          • memory_profiler

          ?1. time 模塊

          這是計算代碼運行所需時間的最簡單、最直接(但需要手動開發(fā))的方法。他的邏輯也很簡單:記錄代碼運行之前和之后的時間,計算時間之間的差異。這可以實現(xiàn)如下:

                ?import?time

          ?start_time?=?time.time()
          ?result?=?5+2
          ?end_time?=?time.time()

          ?print('Time?taken?=?{}?sec'.format(end_time?-?start_time))

          下面的例子顯示了for循環(huán)和列表推導式在時間上的差異:

                ?import?time

          ?#?for?loop?vs.?list?comp
          ?list_comp_start_time?=?time.time()
          ?result?=?[i?for?i?in?range(0,1000000)]
          ?list_comp_end_time?=?time.time()
          ?print('Time?taken?for?list?comp?=?{}?sec'.format(list_comp_end_time?-?list_comp_start_time))

          ?result=[]
          ?for_loop_start_time?=?time.time()
          ?for?i?in?range(0,1000000):
          ?????result.append(i)
          ?for_loop_end_time?=?time.time()
          ?print('Time?taken?for?for-loop?=?{}?sec'.format(for_loop_end_time?-?for_loop_start_time))

          ?list_comp_time?=?list_comp_end_time?-?list_comp_start_time
          ?for_loop_time?=?for_loop_end_time?-?for_loop_start_time
          ?print('Difference?=?{}?%'.format((for_loop_time?-?list_comp_time)/list_comp_time?*?100))

          我們都知道for會慢一些

                ?Time?taken?for?list?comp?=?0.05843973159790039?sec
          ?Time?taken?for?for-loop?=?0.06774497032165527?sec
          ?Difference?=?15.922795107582594?%

          ?2. %%time 魔法命令

          魔法命令是IPython內(nèi)核中內(nèi)置的方便命令,可以方便地執(zhí)行特定的任務。一般情況下都實在jupyter notebook種使用。

          在單元格的開頭添加%%time ,單元格執(zhí)行完成后,會輸出單元格執(zhí)行所花費的時間。

                ?%%time
          ?def?convert_cms(cm,?unit='m'):
          ?????'''
          ????Function?to?convert?cm?to?m?or?feet
          ????'''

          ?????if?unit?==?'m':
          ?????????return?cm/100
          ?????return?cm/30.48

          ?convert_cms(1000)

          結(jié)果如下:

                ?CPU?times:?user?24?μs,?sys:?1?μs,?total:?25?μs
          ?Wall?time:?28.1s

          ?Out[8]:?10.0

          這里的CPU times是CPU處理代碼所花費的實際時間,Wall time是事件經(jīng)過的真實時間,在方法入口和方法出口之間的時間。

          ?3. line_profiler

          前兩個方法只提供執(zhí)行該方法所需的總時間。通過時間分析器我們可以獲得函數(shù)中每一個代碼的運行時間。

          這里我們需要使用line_profiler包。使用pip install line_profiler。

                ?import?line_profiler

          ?def?convert_cms(cm,?unit='m'):
          ?????'''
          ????Function?to?convert?cm?to?m?or?feet
          ????'''

          ?????if?unit?==?'m':
          ?????????return?cm/100
          ?????return?cm/30.48

          ?#?Load?the?profiler
          ?%load_ext?line_profiler

          ?#?Use?the?profiler's?magic?to?call?the?method
          ?%lprun?-f?convert_cms?convert_cms(1000,?'f')

          輸出結(jié)果如下:

                ?Timer?unit:?1e-06?s

          ?Total?time:?4e-06?s
          ?File:?/var/folders/y_/ff7_m0c146ddrr_mctd4vpkh0000gn/T/ipykernel_22452/382784489.py
          ?Function:?convert_cms?at?line?1

          ?Line?#?????Hits?????????Time?Per?Hit???%?Time?Line?Contents
          ?==============================================================
          ??????1???????????????????????????????????????????def?convert_cms(cm,?unit='m'):
          ??????2???????????????????????????????????????????????'''
          ??????3???????????????????????????????????????????????Function?to?convert?cm?to?m?or?feet
          ??????4???????????????????????????????????????????????'''

          ??????5?????????1?????????2.0?????2.0?????50.0?????if?unit?==?'m':
          ??????6???????????????????????????????????????????????????return?cm/100
          ??????7?????????1?????????2.0?????2.0?????50.0?????return?cm/30.48

          可以看到line_profiler提供了每行代碼所花費時間的詳細信息。

          • Line Contents :運行的代碼

          • Hits:行被執(zhí)行的次數(shù)

          • Time:所花費的總時間(即命中次數(shù)x每次命中次數(shù))

          • Per Hit:一次執(zhí)行花費的時間,也就是說 Time = ?Hits X Per Hit

          • % Time:占總時間的比例

          可以看到,每一行代碼都詳細的分析了時間,這對于我們分析時間相當?shù)挠袔椭?/p>

          ?4. memory_profiler

          與line_profiler類似,memory_profiler提供代碼的逐行內(nèi)存使用情況。

          要安裝它需要使用pip install memory_profiler。我們這里監(jiān)視convert_cms_f函數(shù)的內(nèi)存使用情況

                ?from?conversions?import?convert_cms_f
          ?import?memory_profiler

          ?%load_ext?memory_profiler

          ?%mprun?-f?convert_cms_f?convert_cms_f(1000,?'f')

          convert_cms_f函數(shù)在單獨的文件中定義,然后導入。結(jié)果如下:

                ?Line?#???Mem?usage???Increment?Occurrences???Line?Contents
          ?=============================================================
          ??????1?????63.7?MiB?????63.7?MiB???????????1???def?convert_cms_f(cm,?unit='m'):
          ??????2?????????????????????????????????????????????'''
          ??????3?????????????????????????????????????????????Function?to?convert?cm?to?m?or?feet
          ??????4?????????????????????????????????????????????'''

          ??????5?????63.7?MiB?????0.0?MiB???????????1???????if?unit?==?'m':
          ??????6?????????????????????????????????????????????????return?cm/100
          ??????7?????63.7?MiB?????0.0?MiB???????????1???????return?cm/30.48memory_profiler 提供對每行代碼內(nèi)存使用情況的詳細了解。

          這里的1 MiB (MebiByte) 幾乎等于 1MB。1 MiB ?= 1.048576 1MB

          但是memory_profiler 也有一些缺點:它通過查詢操作系統(tǒng)內(nèi)存,所以結(jié)果可能與 python 解釋器略有不同,如果在會話中多次運行 %mprun,可能會注意到增量列報告所有代碼行為 0.0 MiB。這是因為魔法命令的限制導致的。

          雖然memory_profiler有一些問題,但是它就使我們能夠清楚地了解內(nèi)存使用情況,對于開發(fā)來說是一個非常好用的工具

          ?5. 總結(jié)一下

          雖然Python并不是一個以執(zhí)行效率見長的語言,但是在某些特殊情況下這些命令對我們還是非常有幫助的。

          瀏覽 45
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  91在线成人电影 | 大鸡巴操小穴视频 | 午夜久久乐 | 在线免费观看小黄片 | 欧美一区二区三区在线 |