メモリ使用状況の取得
最近、Pythonを使って、大量の画像処理なんかをするようになり、メモリ不足で処理が落ちるということがあったため、メモリの使用状況を確認する方法を勉強してみました。
調べていくといくつか方法があって、
- 現状のPCのメモリ使用状況を取得
- Jupyter Notebookにメモリ使用状況を表示
- 各変数で使用しているメモリ量の取得
というのがあるようでした。
今回はその中で「現状のPCのメモリ使用状況を取得」する方法と「Jupyter Notebookでメモリ使用状況を表示」を試していきましょう。
現状のPCのメモリ使用状況を取得:psutil
現在のメモリ使用状況を取得するには「psutil」というライブラリを使用します。
外部ライブラリなのでまずはpipでインストールします。
pip install psutil
使用するには「mem = psutil.virtual_memory()」としてメモリ情報をまとめて取得し、「メモリ総量(total)」、「メモリ使用量(used)」、「空きメモリ量(available)」、「メモリ使用率(percent)」を指定します。
import psutil
mem = psutil.virtual_memory()
print(mem.total)
print(mem.used)
print(mem.available)
print(mem.percent)
実行結果
8589934592
4863807488
2759139328
67.9
上の例ではメモリ総量は8.6 GB、使用量が4.9 GB、空きメモリ量が2.6 GB、使用率は67.9%となっていることが分かります。
メモリ総量と使用量+空きメモリ量が合わないですが、メモリ負荷を見るにはメモリ使用量や使用率を見ると思うので、とりあえずはこういうものだと認識しておきます。
psutilでCPUの情報を取得
psutilはメモリ情報の取得だけでなく、他のハードウェアの情報も取得することができます。
今回は特に使いそうなものとして、CPUの情報の取得方法も試してみましょう。
CPU情報として取得できるものは以下の通りです。
- CPUの数(スレッド数):cpu_count()
- CPUの数(コア数);cpu_count(logical=False)
- CPU使用率:cpu_percent()
- n秒間の平均CPU使用率:cpu_percent(interval=n)
- 各スレッド毎のCPU使用率:cpu_percent(percpu=True)
import psutil
print(psutil.cpu_count())
print(psutil.cpu_count(logical=False))
print(psutil.cpu_percent())
print(psutil.cpu_percent(interval=1))
print(psutil.cpu_percent(percpu=True))
実行結果
4
2
58.4
65.0
[61.9, 55.4, 61.3, 55.2]
memorySave関数を作ってみた
今回の目的である大量の処理におけるメモリの使用状況の確認をするには、一定時間毎にメモリの使用量や使用率の取得を行うことでしょう。
そこで簡単にメモリの使用状況をCSVファイルに出力できる関数として「memorySave関数」を作成してみました。
プログラムの使い方も合わせたプログラム全体はこちら。
import os
import datetime
import psutil
import csv
import time
cycle_no = 20
interval = 1
start_time = datetime.datetime.now().strftime('%Y%m%d%H%M%S')
default_dirpath = os.getcwd()
output_filepath = os.path.join(default_dirpath, f'{start_time}.csv')
def memorySave(output_filepath):
timenow = datetime.datetime.now().strftime('%Y/%m/%d %H:%M:%S')
mem = psutil.virtual_memory()
used = mem.used
percent = mem.percent
row = [timenow, used, percent]
if not os.path.exists(output_filepath):
with open(output_filepath, 'w') as f_in:
writer = csv.writer(f_in)
header = ['Time', 'Used', 'PercentUsed']
writer.writerow(header)
writer.writerow(row)
elif os.path.exists(output_filepath):
with open(output_filepath, 'a') as f_in:
writer = csv.writer(f_in)
writer.writerow(row)
for i in range(cycle_no):
memorySave(output_filepath)
time.sleep(interval)
使用するライブラリ
memorySave関数内で使用しているライブラリは「os」、「datetime」、「psutil」、「csv」です。
プログラム内で「time」も使用していますが、これは処理中のインターバルを取るために使用しています。
設定部分
次に設定部分です。
cycle_no = 20
interval = 1
start_time = datetime.datetime.now().strftime('%Y%m%d%H%M%S')
default_dirpath = os.getcwd()
output_filepath = os.path.join(default_dirpath, f'{start_time}.csv')
「cycle_no」と「interval」は処理の回数と処理の間隔を定義しているもので、memorySave関数とは関係ありません。
memorySave関数に必要な値は「出力するCSVファイルのパス」です。
そのため、datetime関数を使って現在の時間を取得(start_time = datetime.datetime.now().strftime(‘%Y%m%d%H%M%S’))、現在のフォルダパスを取得(default_dirpath = os.getcwd())、この二つを使って出力するCSVファイルのパスを作成しています(output_filepath = os.path.join(default_dirpath, f'{start_time}.csv’))。
memorySave関数
次にメインのmemorySave関数です。
def memorySave(output_filepath):
timenow = datetime.datetime.now().strftime('%Y/%m/%d %H:%M:%S')
mem = psutil.virtual_memory()
used = mem.used
percent = mem.percent
row = [timenow, used, percent]
if not os.path.exists(output_filepath):
with open(output_filepath, 'w') as f_in:
writer = csv.writer(f_in)
header = ['Time', 'Used', 'PercentUsed']
writer.writerow(header)
writer.writerow(row)
elif os.path.exists(output_filepath):
with open(output_filepath, 'a') as f_in:
writer = csv.writer(f_in)
writer.writerow(row)
最初に現在の時間、メモリ使用量、メモリ使用率を取得し、リストに格納しています。
timenow = datetime.datetime.now().strftime('%Y/%m/%d %H:%M:%S')
mem = psutil.virtual_memory()
used = mem.used
percent = mem.percent
row = [timenow, used, percent]
そして出力するCSVファイルが存在していない場合は、CSVファイルを新規作成し、ヘッダーと合わせて先ほど取得した時間、使用量、使用率を出力します。
if not os.path.exists(output_filepath):
with open(output_filepath, 'w') as f_in:
writer = csv.writer(f_in)
header = ['Time', 'Used', 'PercentUsed']
writer.writerow(header)
writer.writerow(row)
ファイルが存在している場合は、時間、使用量、使用率を追記します。
elif os.path.exists(output_filepath):
with open(output_filepath, 'a') as f_in:
writer = csv.writer(f_in)
writer.writerow(row)
ということでこの関数を呼び出す毎に出力ファイルに時間、使用量、使用率を出力してくれるというわけです。
試験用の処理部分
最後は試験用の処理部分です。
for i in range(cycle_no):
memorySave(output_filepath)
time.sleep(interval)
最初に指定したサイクル数(cycle_no)を繰り返し、その中で「memorySave関数」実行しています。
また一定時間毎に処理をするように「time.sleep」を使って、処理を一時停止しています。
その際の停止する時間が変数intervalです。
実行結果
実行するとこんな感じのファイルが出力されます。
ということで自分のプログラムの繰り返し処理の中に忍ばせておくことで、メモリ使用量や使用率を追えるようになります。
Jupyter Notebookにメモリ使用状況を表示
Jupyter Notebook上で現在のメモリ使用量を表示するには「jupyter-resource-usage」をインストールするだけです。
pip install jupyter-resource-usage
そしてJupyter Notebookを再起動すると、こちらの位置にメモリの使用量が表示されるようになります。
今回はpsutilを使ってメモリの使用状況を取得する方法とJupyter Notebook上にメモリ使用量を表示する方法を紹介しました。
次回はせっかくなので、今回作成したmemorySave関数で出力されたメモリ使用量、使用率のデータをグラフにするプログラムを作成してみましょう。
ではでは今回はこんな感じで。
コメント