Pythonって遅くないですか?
23年度新卒入社の幸村です。
今回は自分の研究のときに使ったものについて紹介です。
自己紹介と研究の概要は「GISでマラリアの研究をしていた新卒エンジニア | cloud.config Tech Blog (cloud-config.jp)」の記事で説明しております。
ちなみに前の記事では書いてなかったのですが、プロフィールの写真はラーメンでなく、酸菜魚(suān cài yú)(スワンツァイユィ) という中国の料理です。本場の中国料理が食べれるようなところでは食べることのできる料理です。こういう日本の料理に限らず海外の料理を食べるのが好きなので、こういうのも紹介していければと思います。
みなさんどのような言語で開発・研究してきましたか?僕は研究ではPythonを主に使って研究していました。
Pythonって簡単で便利ですよね。機械学習系、ネットワーク系、ウェブスクレイピング、アプリ開発、基本的になんでもできて、それを簡単にできるようにするためのモジュールが大量にあります。ほかにも発展させるためのコミュニティもかなり大きいので、わからないことがあれば、大抵のことはググれば何でも出てくるので勉強もしやすい。とにかく、とっつきやすい言語であるとぼくは思います。
ですが、Pythonって遅いんですよ。。。
とにかく遅い。。。
自分の研究では何万とある地点の一時間ごとの気象データを4年分使ったりしていたので、まぁかなりの大きさのデータになるわけです。これを計算するには結構時間がかかります。。。
そこで処理の高速化が必要になり、いろんなことを試しいきました、その際に培った知識を共有していきます。
今回はあくまでも、こういうのがあるよという紹介です。
詳細は自分で調べてください。
NumPy
これはPythonで計算をしたことのあるひとは聞いたことがあるかもしれません。
これは行列、ベクトルなどの計算を早くやってくれるものです。
裏でC言語で動いたりしているので計算が早いんです。
参照:What is NumPy? — NumPy v1.24 Manual
pandas
これもPython触ったことのあるひとは聞いたことがあるものかもしれません。これはデータ分析を行うための便利なモジュールです。
ですが、これをそのまま使うと実は遅いんです。そこでデータの読み込みを高速化させる方法を例として少しあげていきます。ほかにも計算などいろいろあるので調べてみてください。
データ読み込み
CSVの読み込み
pandasってcsvを読み込む際に以下の方法で読むのが一般的だと思います。
Pythonimport pandas as pd
pd.read_csv("large.csv")
ですが、これを以下のように「engine="pyarrow"」という文言を追加するだけでかなり早くなります。
Pythonimport pandas as pd
pd.read_csv("large.csv", engine="pyarrow")
これはcsvをマルチスレッドで読んでいく処理をしています。
これは2022年にpandasに実装された最近のもので、。
CSVが遅い
データってcsvがポピュラーな形だと思いますが、これってあんまりよくないんです。。。
csvはデータを読むだけでcpuの処理をたくさんしたり、メモリを大量に消費したりしてしまいます。。。
pandasって実はほかの種類のファイル形式にも対応しています。
データをほかの人に共有しなくていいときなどcsvじゃなくても良いときは、parquetやpickleなどを使いましょう。
これらは読み込みがcsvに比べて高速です。
読み込みも簡単です。読み込んでさえしまえば、普通のDataFrame型で使えるので、かなり便利です
Pythonimport pandas as pd
# parquet
pd.read_parquet("large.parquet", engine="fastparquet")
# pickle
pd.read_pickle('large.pkl')
参照:pandas documentation — pandas 2.0.0 documentation (pydata.org)
Dask
大量のデータを扱う際にメモリに乗らなかったりすることってあると思います。pandasでも解決できたりするのですが、daskを使うことでより簡単に解決できます。Daskではデータを分割して読み込んでいくため、メモリの使用量が少ないというメリットがあります。
参照:Dask DataFrame — Dask documentation
RAPIDS
使っている環境にNvidia製のGPUがある場合、GPUを使用して計算できます。
pandasやNumPyをそのまま使用するとCPU上で計算を行いますが、RAPIDSを使うとGPU上で計算しくれます。これもdaskと一緒につかうことで少ないリソースで大きなデータの処理をできたりします。
Numba
pythonの中の関数をLLVMコンパイラでコンパイルできる形にして、高速化させようというものす。C言語のように一度、変換しないといけないので、その際の実行時間は長いですが、一度できてしまうとかなり早くなります。for文を回すときとかに有効です。
参照:Numba: A High Performance Python Compiler (pydata.org)
並列処理・並行処理(multithreading・multiprocessing)
これはPythonに限った話ではないですが、pcのリソースを物理的にたくさん使って早くしようというものです。
英語のYouTubeですが、threading vs multiprocessing in python - YouTube のビデオが視覚的にもわかりやすく表現されていました。
最後に
今回は便利なPythonの動作を高速化させるための技術を紹介しました。Pythonでは大量のデータを裁きたいひとは参考にしてみてください。
機械学習やったり、データサイエンスしたりしていると使えるかなと思います。
今回紹介したのはあくまでも一部ですので、詳細、ほかの高速化手段は調べてみてください。実際に手を動かしたり、技術の中でどのような動きがされているのかを勉強すると自分のコードを最適化するための勉強になります。