🏎️

[RAPIDS]GPU版scikit-learnで機械学習を爆速にしよう

2022/07/21に公開

RAPIDS

RAPIDSとは、NVIDIA社が提供するオープンソースライブラリ群(と呼べばいいのか)で、極々簡単にいうならばPandasやScikit-learn、networkxなど日頃データサイエンスでよく使うPythonライブラリのGPU版です。元となっているライブラリの使用感をほぼそのままに、かつGPUの力を使って高速に処理できるようになります。
要はGPUの恩恵をもっと幅広く受けられるようにしようぜ、というものですね。今回、少しRAPIDSに触れる機会がありその凄さを感じ取ることができたのでその実装を含めて紹介します。

参考
https://rapids.ai/about.html

・・ここまで前回のコピペ
https://zenn.dev/littledarwin/articles/eeceb78ca14f57

取り組んだこと

  • GoogleColabでの実装を行います
  • 今回は、scikit-learnとそのGPU版であるcumlの処理速度差を確認します

実装方法

こちらのページにあるGoogleColabのリンクを開き、notebookを上から順に実行していきます。
https://rapids.ai/start.html

インストール作業においていくつか注意がありますが、前回と同じなのでここでは割愛します。
https://zenn.dev/littledarwin/articles/eeceb78ca14f57

scikit-learnのGPU版 cumlの速さを試してみる

大きめサイズのデータの重回帰分析モデリングを行い、CPUとGPUでの速度差を調べました。

  • データセットの作成
    速度差を感じ取りやすいようにデータは大きめのものを作ります。
#ダミーのデータセット(大サイズ)を作成
import numpy as np
dummy_data = np.random.randn(500000, 100)
  • データフレームの作成
    この工程、不要かなとも思いましたが一応。再びcudf(PandasのGPU版)を登場させました。
#cudfはPandasのGPU版
import pandas as pd
import cudf
df = pd.DataFrame(dummy_data, columns = ["{}".format(i) for i in range(100) ])
df_cudf = cudf.DataFrame.from_pandas(df)
df_cudf.shape

CPUでの機械学習

いつも通りの作業

#説明変数と目的変数に分ける(CPU版 いつも通り)
X = df.iloc[:, 1:]
y = df.iloc[:, 0]
#train_test_splitのCPU版(いつも通り)
%%time
from sklearn.model_selection import train_test_split as train_test_split_cpu
X_train, X_test, y_train, y_test = train_test_split_cpu(X, y, train_size=0.8)

CPU times: user 455 ms, sys: 2.41 ms, total: 458 ms
Wall time: 456 ms

#重回帰分析のCPU版(いつも通り)
%%time
from sklearn.linear_model import LinearRegression as lr_cpu
lr = lr_cpu()
lr.fit(X_train, y_train)
lr.score(X_test, y_test)

CPU times: user 9.06 s, sys: 244 ms, total: 9.31 s
Wall time: 5 s

GPUでの機械学習

どれくらい速くなるのでしょうか。

#今回の主役ライブラリcuml。scikit-learnのGPU版です。
import cuml
#説明変数と目的変数に分ける(GPU版)
X_cudf = df_cudf.iloc[:, 1:]
y_cudf = df_cudf.iloc[:, 0]
#train_test_splitのGPU版
#scikit-learnと記述がまんま同じなので、ここでは分かりやすくするため_gpuなどの名称を付けています
%%time
from cuml.model_selection import train_test_split as train_test_split_gpu
X_train_gpu, X_test_gpu, y_train_gpu, y_test_gpu = train_test_split_gpu(X_cudf, y_cudf, train_size=0.8)

CPU times: user 42 ms, sys: 23.1 ms, total: 65.1 ms
Wall time: 71.8 ms

#重回帰分析のGPU版
%%time
from cuml.linear_model import LinearRegression as lr_gpu
lr = lr_gpu()
lr.fit(X_train_gpu, y_train_gpu)
lr.score(X_test_gpu, y_test_gpu)

CPU times: user 91.8 ms, sys: 22.2 ms, total: 114 ms
Wall time: 113 ms

整理

タスク sklearn cuml
train_test_split 456ms 71.8ms
LinearRegression 5000ms 113ms

仕様通り、高速に処理ができていることがわかりました。

まとめ

さすがGPUという感じではあります。しかし今回は差が見えやすいようにデータサイズを大きくしましたし、元々CPUだって我慢できないほど時間がかかっているわけではないので恩恵は微妙かもしれません。
とはいえ、メソッドの記述がほぼscikit-learnと同じであることを考えると新たに覚えることもありませんし「やるだけ得」という考えもありますね。
GoogleColabだとそれ以上に環境構築に時間かかるじゃんというのは秘密です。

Discussion