ハンズオンを通してAmazon SageMaker AIでカスタムモデルを作成してみる
お疲れさまです。とーちです。
前回に引き続き、Amazon SageMaker Immersion Dayのハンズオンをやっています。
今回は、Amazon SageMaker(以後、SageMaker)でカスタムモデルを実装する方法について学んだことを共有したいと思います。
料金について
今回の範囲では、Amazon SageMaker Studio JupyterLab
料金、Amazon SageMaker トレーニング
料金と Amazon SageMaker ホスティング: リアルタイム推論
の料金がかかると思われます。料金の詳細は以下の公式ページをご参照ください。
Amazon SageMaker におけるコンテナの使用方法
Amazon SageMaker では、スクリプトの実行、トレーニング、デプロイのすべてのフェーズでDocker(以後、Docker)コンテナを使用します。
- Amazon SageMaker の組み込みアルゴリズムの使用
- 最もマネージドな方法
- ユーザーが行うのはハイパーパラメータの設定とデータの提供のみ
- Amazon SageMaker の事前構築済みコンテナイメージの使用
- フレームワーク(TensorFlow、PyTorch等)の実行環境のみを提供
- ユーザーがトレーニング処理用のコードを用意
- Amazon SageMaker の事前構築済みコンテナイメージの拡張
- 独自のコンテナイメージの実装
と、ハンズオンテキストには記載があるのですが、組み込みアルゴリズムと事前構築済みコンテナイメージの違いがよく分からなかったので調べてみました。
組み込みアルゴリズムは前回のブログで紹介した方法がそれにあたります。
xgb = sagemaker.estimator.Estimator(container,
role,
instance_count=1,
instance_type='ml.m4.xlarge',
output_path='s3://{}/{}/output'.format(bucket, prefix),
sagemaker_session=sess)
xgb.fit({'train': s3_input_train, 'validation': s3_input_validation})
このコードを見るとわかるのですが、Estimatorにはどのような処理で機械学習トレーニングを行うかが書かれたコードの指定はありません。
mnist_estimator = TensorFlow(
entry_point='mnist-2.py',
role=role,
instance_count=2,
instance_type='ml.c5.xlarge',
framework_version='2.1.0',
py_version='py3',
distribution={'parameter_server': {'enabled': True}}
)
mnist_estimator.fit(training_data_uri)
対して今回使用するこちらのコードでは、entry_pointとして mnist-2.py
と記載されています。これは機械学習トレーニングを行う際にこのプログラムを使用してトレーニングを行うということを示しています。
つまり、「Amazon SageMaker の組み込みアルゴリズム」と「Amazon SageMaker の事前構築済みコンテナイメージ」の使い方として最も異なる点はユーザーがトレーニング処理用のコードを用意するかどうかです。
ちなみにSageMakerが用意している組み込みアルゴリズムは以下のページで確認することができます。
TensorFlow スクリプトモード について
TensorFlow スクリプトモード は、Amazon SageMaker 上で TensorFlow の学習スクリプトを最小限の修正で実行できる機能です。
ユーザーがトレーニング処理用のコードを用意するので、Amazon SageMaker の事前構築済みコンテナイメージの使用 に該当します。
主な特徴
- Amazon SageMaker Python SDK による自動スクリプト転送
- 環境変数の自動設定
- 複数のファイル形式のサポート(Python スクリプト、モジュール、シェルスクリプト)
TensorFlow スクリプトモードを使用するには
TensorFlow スクリプトモード を使用するには、sagemaker.tensorflow.TensorFlow
エスティメータを作成する際に、
entry_point
パラメータで実行したい Python スクリプトを指定します。この際、py_version
パラメータは
使用する Python 環境のバージョンを指定するために使用します。
なお、Amazon SageMaker Python SDK の sagemaker.tensorflow モジュールのドキュメントを読むとimage_uriも指定出来るようなのでこれを指定した場合は、 「独自のコンテナイメージの実装」方式でのトレーニング実行になるのかなと思います。
ハンズオン:MNIST 分類モデルの実装
今回のハンズオンでは、以下を実施します:
- MNIST データセットを使用した分類モデルの作成
- TensorFlow 2.1.x を使用
- リアルタイム推論エンドポイントの構築
データセットの準備
MNIST データセットは Amazon Simple Storage Service(以後、Amazon S3)の公開バケットに格納されています。ちなみにMNIST データセットとは手書き数字の画像のデータセットです。
bucket_name = f'sagemaker-sample-data-{region}'
dataset_path = 'tensorflow/mnist'
保存されているファイルは以下の4つです
train_data.npy
:学習用の画像データeval_data.npy
:評価用の画像データtrain_labels.npy
:学習用の正解ラベル(数字の答え)eval_labels.npy
:評価用の正解ラベル(数字の答え)
トレーニング処理用のコード
ハンズオンで用意されているトレーニング処理用のコードはTensorFlowが提供している手書き数字認識(MNIST)のサンプルコードをSageMaker向けに改修したものとのことです。
主要な変更点はSM_MODEL_DIRへの対応とSM_MODEL_DIRへのモデルの出力です。
parser.add_argument('--sm-model-dir', type=str, default=os.environ.get('SM_MODEL_DIR'))
上記の行で、トレーニング用スクリプトに--sm-model-dir
という引数を追加しています。また、環境変数 SM_MODEL_DIR
に入っている値をその引数のデフォルト値としています。
SM_MODEL_DIRはSageMakerでトレーニングジョブを実行すると自動で設定される環境変数であり、デフォルトでは、 /opt/ml/model
です。
この環境変数は、トレーニングしたモデルのアーティファクトを出力するディレクトリを示しており、このディレクトリに置かれたファイルはトレーニング終了時にS3に出力されるようになっています。(ご参考)
SageMaker内トレーニングジョブ内のコンテナのパスとS3バケットの関係は以下の図がわかりやすかったので載せておきます。
※画像はAmazon SageMaker AI によって管理されるトレーニングストレージパスのマッピング - Amazon SageMaker AIより
コード内で作成されたモデルは最終的に以下の行で、/opt/ml/model
に保存されています。( args.sm_model_dir
で --sm-model-dir
に指定された値を参照)
# To export the model as h5 format use model.save('my_model.h5')
mnist_classifier.save(os.path.join(args.sm_model_dir, '000000001'))
モデルのトレーニング
mnist_estimator = TensorFlow(
entry_point='mnist-2.py',
role=role,
instance_count=2,
instance_type='ml.c5.xlarge',
framework_version='2.1.0',
py_version='py3',
distribution={'parameter_server': {'enabled': True}}
)
estimator.fit(training_data_uri)
上記のコードで先程のトレーニング処理用のコードを指定したうえで、機械学習モデルのトレーニングを行っています。
estimator作成時に指定しているパラメータを簡単に記載しておきます。
estimatorの主要なパラメータの説明
- entry_point: トレーニングに使用するコードを指定
- py_version: Python ランタイムのバージョン指定
- distribution: 分散学習の設定を指定するパラメータ
- instance_type: トレーニングに使用するインスタンスタイプの指定
- framework_version: TensorFlow のバージョン指定
fitメソッドでトレーニング実行です。training_data_uriにはMNISTのデータセットが入ったAmazon S3バケットのパスが指定されています。
モデルのデプロイ
predictor = estimator.deploy(
initial_instance_count=1,
instance_type='ml.c5.xlarge'
)
TensorFlow Serving コンテナを使用して、モデルをリアルタイム推論エンドポイントとしてデプロイします。
推論の実行
predictions = predictor.predict(train_data[:50])
for i in range(0, 50):
prediction = np.argmax(predictions['predictions'][i])
label = train_labels[i]
print('prediction is {}, label is {}, matched: {}'.format(prediction, label, prediction == label))
上記のコードで作成したエンドポイントに予測をさせています。 predictor.predict
でエンドポイントに対して予測させたいデータを投げて、結果をfor文で参照している形です。
for文の中では、エンドポイントから受け取ったデータ(prediction)と正解データ(label)と予測と正解データが合っているか(prediction == label)を表示しています。
まとめ
というわけで、ハンズオンを通して、Amazon SageMaker AIでカスタムモデルを作成する方法を学びました。
概要を理解するだけでもなかなか難しいですね。
以上、とーちでした。