2019年11月20日水曜日

[python] killed: 9 でプログラムが終了してしまう

pythonで書いたスクリプトでデータ処理を行なっていて、時間がかかりそうだったので帰る前に初めて放っておいたのだが、今日来てみたら、killed: 9 というメッセージとともにプログラムが最後まで終わらずに終了していた。染色体ごとの処理で10つのうちの8番染色体までファイルができていた。8の途中で処理が終わった可能性があるのでここから再度解析した方がいいだろう。

このkilled: 9を検索して調べてみると、python処理を行なっている途中でスクリプトがメモリを消費しすぎている際にカーネルがこの処理をkillしてしまうようだった。どんな状態なのか見るために、8番染色体の処理から再開して、メモリプレッシャーを観察することにした。解析はmacbook pro 2015  Core i7 16GbRAMで行なっている。

始めるとすぐにファンが最大に唸り出して筐体がほんのり暖かくなってくる。最初の出力がではじめたあたりでメモリ使用をみると、以下のような感じだった。


 結構使っていたのね、知らなかった。だが、しばらくするとメモリプレッシャーはさらに高くなっていった。


この頃になるとGUIの操作の方にも影響が出てきて、画像がカクついたり処理が遅れたりしはじめた。8番染色体が終わって次の染色体に映るところで少し楽になったが、次からさらにきつくなりはじめた。


また終了してしまったら嫌だなと思いつつ見守っていると、メモリプレッシャーはさらに高くなって、とうとう真っ赤になってしまった。


 この状態になって途中で終わったのか、と納得した。とても単純な処理を繰り返しているだけだが、読み込んだデータを格納して処理していくとこで大量にメモリを食っているのではないかと思った。本職の人だったらこういうのも考えてプログラムを書くのだろうが、その辺の知識がまだ足りないのだろう(バイオインフォの講習でも「よくある処理の効果的なプログラミング」とかやってくれるといいんだけれど。。)。

検索してみると、pythonを使用しているときに、メモリを解放してやる必要があるようだ。pythonにはgabage collectionの機能があり、不要になったメモリを自動的に解放してくれる機能があるらしい。ただ、大量のデータを扱う場合に自分で要素を削除して、しかるのちにメモリを解放することもできるみたいだ。

python公式 3.8.0 gc --- ガベージコレクタインターフェース
https://docs.python.org/ja/3/library/gc.html

import gc

# いらなくなったデータの削除
del Data_ChrX
# メモリを解放
gc.collect()

上の処理で違いが出てくるかちょっと試してみたい。