AWS で銀行向け説明可能な商品推薦システムを構築
本文の状態
日本語全文を表示中
詳細モードで約16分の本文を読めます。
同じ出来事の情報源
この情報源を基点に整理
AWS Machine Learning Blog
AWS は、深層学習を用いた説明可能な次期ベスト製品推薦システムを構築するアーキテクチャと設計思想について、Amazon SageMaker AI と PyTorch を活用した事例として紹介している。
AI深層分析を開く2026年7月28日 09:21
AI深層分析
キーポイント
NBP システムの課題と解決アプローチ
銀行が保有する膨大な顧客データから複雑な時間的パターンを捉えるのは困難であり、従来のルールベースや協調フィルタリングでは不十分であるため、深層学習による説明可能なシステムが必要となる。
マルチタワーニューラルネットワークの採用
本稿では、顧客ごとの説明性を提供するために学習されたアテンションを活用したマルチタワーニューラルネットワークアーキテクチャの設計思想と理由を詳述している。
AWS サービスによる実装基盤
研究段階から本番環境への移行において、Amazon SageMaker AI、S3、AWS Glue、CloudWatch などの AWS サービスが連携して機能する構成を示している。
大規模データ処理の設定
chunksize を500万に設定してバッチ処理を行い、n_workers に4を指定して並列実行する構成が示されている。
マルチタワーアーキテクチャの採用
顧客データの構造が異なるため、単一のネットワークではなくシークエンス、取引、顧客属性、行動セグメントを処理する4つの専門化されたタワーを使用する。
重要な引用
Building a deep learning-based explainable next-best-product recommendation system helps banking institutions predict which product a customer needs next.
Traditional rule-based systems and collaborative filtering approaches often fail to capture the complex temporal patterns in customer product adoption journeys.
This is an architectural overview, not a step-by-step deployment guide.
chunksize = 5_000_000
編集コメントを表示
編集コメント
本記事は、単なるツールの紹介ではなく、金融分野特有の規制や信頼性要件を満たすための「説明可能性」を技術的にどう実装するかという設計思想に焦点を当てている。AWS のエコシステムを活用する開発者にとって、研究段階から本番運用までの移行プロセスにおけるベストプラクティスを知る上で有益な資料である。
Source Article
元記事を日本語で読む
本文に関係しない購読案内、埋め込み通知、サイト内プロモーションは除いています。
深層学習を活用した説明可能な次期最適商品推薦システムを構築することで、金融機関は顧客が次に必要とする商品を予測できるようになります。銀行には取引履歴、保有製品記録、人口統計情報、行動パターンなど、膨大な顧客データが蓄積されています。しかし、これらのデータを具体的なアクションにつながるパーソナライズされた商品推薦に変換することは依然として大きな課題です。
従来のルールベースのシステムや協調フィルタリング手法では、顧客が製品を採用する過程における複雑な時系列パターンの捕捉が困難でした。
本稿では、Amazon SageMaker AI と PyTorch を活用した次期最適商品(NBP)推薦システムのアーキテクチャと設計思想について解説します。多層ニューラルネットワークの採用理由や、学習されたアテンション機構が顧客ごとに説明可能性を提供する仕組み、さらに AWS の各サービスが連携して研究段階から本番環境への移行をどのように支えるかについても詳述します。
これはステップバイステップのデプロイガイドではなく、アーキテクチャの概要です。金融サービスに限らず、多様な顧客データを持つ他のドメインで推薦システムを構築する際にも、ここで紹介するアーキテクチャパターンが、より精度が高く解釈可能なモデル設計に役立つはずです。
前提条件
本稿で紹介するアーキテクチャのパターンやコード例を実践するには、以下の準備が必要です。
このソリューションを実行するには、SageMaker AI、Amazon Simple Storage Service (Amazon S3)、AWS Glue、Amazon CloudWatch へのアクセス権限を持つ AWS アカウントが必要です。
また、以下の AWS サービスにアクセスできる AWS Identity and Access Management (IAM) の実行ロールも必要です。このソリューションに必要なリソースのみを対象とした最小権限のポリシーを作成してください。
- SageMaker AI – 学習ジョブ、処理ジョブ、バッチ変換ジョブ、モデル、エンドポイント、エンドポイント構成、パイプライン、実験、モニタリングスケジュールの作成、説明、開始、停止、削除。リアルタイム推論には InvokeEndpoint を使用します。
- Amazon S3 – データバケットへの読み書きアクセス権限。バケットの作成と削除。オブジェクトの一覧表示、アップロード、ダウンロード、削除。
- AWS Glue – ETL ジョブの作成、実行、削除。クローラーの作成と削除。データカタログデータベースおよびテーブルの作成と削除。
- CloudWatch – ロググループ、ログストリーム、メトリクスへの読み書きアクセス権限。クリーンアップ時にロググループを削除します。
- IAM – ロールの作成と削除。ポリシーの添付と剥離。PassRole(指定された実行ロール ARN に制限され、sagemaker.amazonaws.com および glue.amazonaws.com に対してスコープが設定されているもの)。
SageMaker AI で最小権限の IAM ポリシーを作成する際のガイドについては、SageMaker AI のアイデンティティベースのポリシー例を参照してください。
- Python 3.11 以降と PyTorch の基本的な知識があること
本リコメンダーシステム構築に必要なパッケージ:
- Python 3.11 以降
- PyTorch 2.9 以降
- Pandas 2.3 以降
- NumPy 2.3 以降
- scikit-learn 1.7 以降
- Dask 2025.11 以降
デプロイ前に仮想環境を使用し、pip-audit などのツールで依存関係に既知の脆弱性がないかスキャンすることを推奨します。
- 深層学習の基本概念(埋め込み表現、リカレントネットワーク、アテンション機構など)に関する基礎知識
注意:本ソリューションをデプロイすると、SageMaker AI のトレーニングジョブ(ml.g5.12xlarge GPU インスタンス)、SageMaker AI エンドポイント、Amazon S3 ストレージ、AWS Glue ジョブなど課金対象の AWS リソースが作成されます。継続的な請求を防ぐため、本記事末尾のクリーンアップ手順に従ってください。
ソリューション概要
本ソリューションは、顧客データの異なる側面をそれぞれ処理する 4 つの専門化されたニューラルネットワーク層(タワー)を持つマルチタワー深層学習アーキテクチャを採用しています。これらのタワーは、学習されたアテンション機構によって融合され、高い精度と顧客ごとの説明可能性の両方を提供します。
以下の図に、本ソリューションの高レベルなアーキテクチャを示します。

このアーキテクチャは、銀行業界でよく見られる課題に対応しています。具体的には、クレジットカード、預金、保険、ローン、住宅ローンなど複数の商品カテゴリの中から、顧客が次に購入する可能性が高い商品を予測し、かつ規制要件を満たす説明可能な結果を提示することです。
Tech stack
以下の表は、本ソリューションにおける技術選定とその役割を要約したものです。
| コンポーネント | 技術 | 目的 |
|---|---|---|
| ETL & データ処理 | AWS Glue (PySpark) | 大規模なデータ統合、サービスマッピング、特徴量エンジニアリングのためのサーバーレス Spark ベースの ETL |
| 深層学習フレームワーク | PyTorch | 動的計算グラフ、研究から本番環境への柔軟な移行、ネイティブ GPU サポート |
| 特徴量エンジニアリング | Pandas, Dask, PyArrow | ML 固有の特徴量エンジニアリング(シーケンス作成、ウィンドウ集約) |
| ML ユーティリティ | scikit-learn | ラベルエンコーディング、標準スケーリング、トレーニング/テスト分割、評価指標 |
| トレーニング計算リソース | SageMaker AI (ml.g5.12xlarge) | 192 GB RAM、4× NVIDIA A10G GPU |
| データストレージ | Amazon S3 | 生データ、中間データ、処理済みデータの Snappy 圧縮 Parquet ファイル |
| データカタログ | AWS Glue Data Catalog | スキーマ管理、テーブルメタデータ、自動発見用のクローラー |
| モデルレジストリ | SageMaker AI モデルレジストリ | バージョン管理されたモデルアーティファクト、承認ワークフロー |
| 推論 | SageMaker AI Batch Transform / エンドポイント | バッチ処理およびニアリアルタイム予測 |
| オーケストレーション | Amazon SageMaker Pipelines | エンドツーエンドの ML パイプラインオーケストレーション |
| モニタリング | CloudWatch | トレーニング指標、推論レイテンシ、モデルドリフト検出 |
なぜ PyTorch を選ぶのか
本ソリューションでは、可変長のシーケンス処理に不可欠な pack_padded_sequence に対応する動的計算グラフの構築や、複数のアーキテクチャ段階における迅速な試行錯誤、そして SageMaker AI のトレーニングジョブや推論コンテナとのネイティブ統合を実現するために PyTorch を採用しています。
なぜ Amazon S3 で Parquet を使うのか
本ソリューションでは、データを Snappy 圧縮された Parquet 形式で Amazon Simple Storage Service (Amazon S3) に保存します。Parquet の列指向フォーマットにより、広大なファイルの一部のみを読み込む「カラムプルーニング」や、不要な行グループをスキップする「プレディケートプッシュダウン」が可能となり、CSV と比較して 3〜5 倍の圧縮効率を実現します。また、読み込みごとに再解析を行う必要なくデータ型も保持されます。
なぜ AWS Glue を ETL に使うのか
本プロジェクトでは、サーバーレスで自動スケーリングするデータ処理のために、PySpark で動作する AWS Glue ジョブを利用しています。AWS Glue はネイティブな Spark 統合機能を提供し、柔軟なスキーマを扱える DynamicFrame API や、自動的に Data Catalog に登録される機能、増分処理のためのジョブブックマーク、そして DPU (Data Processing Unit) 課金に基づくコスト効率の良さを実現します。
データパイプラインのアーキテクチャ
データパイプラインは 2 つの段階で構成されています。まず AWS Glue ETL ジョブによるデータの統合を行い、続いて Amazon SageMaker Processing ジョブで機械学習に特化した特徴量エンジニアリングを実施します。
AWS Glue を用いたデータ統合
銀行のデータは、通常、複数のソースシステムから不整合なスキーマで流入します。AWS Glue の ETL ジョブはこのスキーマを正規化し、生取引タイプを統一されたサービスカテゴリにマッピングします。さらに、顧客ごとに時系列記録として全データを結合し、時間的な特徴量エンジニアリングを行います。処理済みの出力は Parquet 形式で Amazon S3 に書き込まれ、AWS Glue データカタログに登録されます。
Amazon SageMaker Processing を用いた ML 固有の特徴量エンジニアリング
AWS Glue ジョブが統合履歴を生成した後、Amazon SageMaker Processing ジョブが顧客ごとの商品採用シーケンスを作成します。また、Dask を活用して並列処理を行い、7 日、30 日、60 日、180 日、365 日の各時間窓における取引集計を計算し、モデル入力用にシーケンスを固定長にパディングします。
大規模データの扱い
利用可能なメモリを超える大規模データセットに対しては、メタデータ検査に PyArrow を、並列チャンク処理に ProcessPoolExecutor を用いた並列チャンク処理戦略を採用しています。バッチ間の明示的なガベージコレクションと、メモリスパイクを防ぐための増分マージも実施します。
import gc
from concurrent.futures import ProcessPoolExecutor
chunksize = 5_000_000
n_workers = 4
for batch_start in range(0, total_chunks, n_workers):
with ProcessPoolExecutor(max_workers=n_workers) as executor:
futures = [
executor.submit(process_chunk_range, input_path, output_path, i, start_row, end_row)
for i in range(batch_start, min(batch_start + n_workers, total_chunks))
]
for future in futures:
future.result()
gc.collect() # Force garbage collection between batches注:実際の顧客データを扱う際は、セキュリティに関する考慮事項 セクションを参照し、個人識別情報(PII)の取り扱いや規制コンプライアンス、データガバナンスに関するガイダンスを確認してください。
モデルアーキテクチャ
本モデルはマルチタワーアプローチを採用しており、各タワーが顧客データの一種類を処理する専門化を行い、その後、注意機構(attention-based)による融合メカニズムで統合します。
なぜ単一ネットワークではなくマルチタワーなのか
顧客データには、根本的に異なる構造を持つ種類が複数存在します。シーケンスは離散 ID の順序付きリストであり、取引記録は数値の集約値です。人口統計情報はカテゴリカルと数値の特徴が混在しており、行動セグメントはカテゴリカルコードで表されます。
これらすべてのデータを同じ層に通すことは、モデルの容量を無駄にすることになります。そこで本アーキテクチャでは、各データタイプに特化した 4 つの専用タワーを採用しています。
| タワー | 入力タイプ | アーキテクチャ | 出力 |
|---|---|---|---|
| シーケンスタワー | 製品採用履歴(固定長にパディング済み) | nn.Embedding → 2層 GRU → アクティブ製品数との融合 | 64次元ベクトル |
| 取引タワー | 時間ウィンドウ付き取引特徴量 | ReLU と Dropout を備えた 2 層 MLP (128 → 64) | 64次元ベクトル |
| 顧客タワー | 人口統計、収入、家族構成、口座特徴量 | ReLU と Dropout を備えた 2 層 MLP (128 → 64) | 64次元ベクトル |
| 行動タワー | セグメンテーションコード、ロイヤリティ、利用パターン | ReLU と Dropout を備えた 2 層 MLP (128 → 64) | 64次元ベクトル |
シーケンス・タワー:時系列パターンの捕捉
シーケンス・タワーは、2 層の Gated Recurrent Unit (GRU) を用いて顧客の商品採用履歴を処理します。このアーキテクチャの核心となる理由は、単に顧客が保有する商品ではなく、「どの順序で商品を導入したか」という時系列のパターンを捉えることができる点にあります。
class SequenceTower(nn.Module):
def __init__(self, num_products, embedding_dim=32, hidden_dim=64, dropout=0.2):
super().__init__()
self.embedding = nn.Embedding(num_products + 1, embedding_dim, padding_idx=0)
self.gru = nn.GRU(
input_size=embedding_dim, hidden_size=hidden_dim,
num_layers=2, batch_first=True, dropout=dropout
)
self.active_count_layer = nn.Sequential(
nn.Linear(1, hidden_dim // 2), nn.ReLU(), nn.Dropout(dropout)
)
self.fusion = nn.Sequential(
nn.Linear(hidden_dim + hidden_dim // 2, hidden_dim),
nn.ReLU(), nn.Dropout(dropout)
)
def forward(self, sequence, seq_length, active_count):
embedded = self.embedding(sequence)
packed = nn.utils.rnn.pack_padded_sequence(
embedded, seq_length.cpu().clamp(min=1),
batch_first=True, enforce_sorted=False
)
_, hidden = self.gru(packed)
seq_features = hidden[-1]
active_features = self.active_count_layer(active_count)
return self.fusion(torch.cat([seq_features, active_features], dim=1))なぜ LSTM ではなく GRU を選ぶのか
GRU はリセットゲートと更新ゲートの 2 つのゲートを持つ一方、LSTM は入力・忘却・出力の 3 つのゲートを備えています。この構造の違いにより、パラメータ数は約 33% 削減されます。20 項目以内といった短いシーケンスにおいては、GRU は LSTM と同等の性能を発揮しつつ、学習速度はより速くなります。また、更新ゲートの補間機構が、自然な残差接続のような勾配パスを形成する点も利点です。
なぜ pack_padded_sequence を使用するのか
顧客のシーケンスデータには長さのばらつきがあります。pack_padded_sequence を使用することで、GRU がパディングトークンを無視し、ゼロ埋めされた位置からのノイズを学習することを防ぎます。
タワー・アテンション機構:説明可能性を備えた学習による融合
単純な結合(concatenation)ではなく、このアーキテクチャではタワーの出力を融合させるために学習されたアテンション機構を採用しています。これにより、SHAP や LIME といった事後解釈手法に依存することなく、顧客ごとの説明可能性を実現できます。
class TowerAttentionMechanism(nn.Module):
def __init__(self, hidden_dim=64, num_heads=4, dropout=0.1):
super().__init__()
self.tower_attention = nn.MultiheadAttention(
embed_dim=hidden_dim, num_heads=num_heads,
dropout=dropout, batch_first=True
)
self.context_weighting = nn.Sequential(
nn.Linear(hidden_dim * 4, 4), nn.Softmax(dim=1)
)
def forward(self, tower_outputs):
stacked = torch.stack(tower_outputs, dim=1) # [batch, 4, 64]
attended, _ = self.tower_attention(stacked, stacked, stacked)
stacked = stacked + attended # Residual connection
concat = torch.cat(tower_outputs, dim=1) # [batch, 256]
tower_weights = self.context_weighting(concat) # [batch, 4]
weighted_outputs = [
tower_outputs[i] * tower_weights[:, i:i+1]
for i in range(4)
]
return weighted_outputs, tower_weightsタワーの重みは顧客ごとに異なります。取引履歴が豊富な顧客には「取引タワー」の重みを高く設定し、取引数は少ないものの明確な属性情報を持つ新規顧客には「顧客タワー」の重みを高く設定します。この適応性により精度が向上するだけでなく、担当者の関係構築や規制当局への説明においても自然な根拠を提供できます。
コンテキスト認識融合:安定した学習のための残差ブロック
重み付けされたタワーの出力は、残差接続を備えた融合ネットワークを経由します。残差接続は、学習中の勾配フローを改善し、追加の深さが必要ない場合にネットワークが恒等写像(アイデンティティマッピング)を学習できるように支援します。
class ContextAwareFusion(nn.Module):
def __init__(self, hidden_dim=64, dropout=0.2):
super().__init__()
self.initial_projection = nn.Linear(hidden_dim * 4, hidden_dim)
self.fusion1 = nn.Sequential(
nn.Linear(hidden_dim, hidden_dim * 2), nn.LayerNorm(hidden_dim * 2),
nn.ReLU(), nn.Dropout(dropout), nn.Linear(hidden_dim * 2, hidden_dim)
)
self.layer_norm1 = nn.LayerNorm(hidden_dim)
self.fusion2 = nn.Sequential(
nn.Linear(hidden_dim, hidden_dim), nn.ReLU(), nn.Dropout(dropout)
)
self.layer_norm2 = nn.LayerNorm(hidden_dim)
def forward(self, weighted_outputs):
concat = torch.cat(weighted_outputs, dim=1)
projected = self.initial_projection(concat)
out1 = self.layer_norm1(projected + self.fusion1(projected)) # Residual
out2 = self.layer_norm2(out1 + self.fusion2(out1)) # Residual
return out2特徴重要度モジュール:内蔵された説明可能性
金融規制当局はモデルの説明可能性を求めています。事後解析手法に依存するのではなく、このアーキテクチャには「特徴重要度モジュール」が組み込まれており、順伝播の一部として顧客ごとの重要度スコア(合計 1.0)を生成します。
class FeatureImportanceModule(nn.Module):
def __init__(self, hidden_dim=64):
super().__init__()
self.feature_contribution = nn.Sequential(
nn.Linear(hidden_dim, 4), nn.Softmax(dim=1)
)
def forward(self, fused_features, tower_weights):
feature_importance = self.feature_contribution(fused_features)
return feature_importance * tower_weightsこれにより、「この顧客に対する推薦の 40% は製品シークエンスによるもので、30% が取引パターン、20% が人口統計情報、10% が行動セグメントによるものです」といった出力が得られます。リレーションシップマネージャーはこれを活用して、各顧客との対話を最適化できます。
学習戦略
以下の表は、学習設定と各選択の根拠を要約したものです。
パラメータ
値
根拠
Optimizer
Adam (lr=0.001, weight_decay=1e-5)
パラメータごとの適応学習率、軽量な L2 正則化
Loss
CrossEntropyLoss
多クラス分類の標準的な手法で数値的に安定している
LR Scheduler
ReduceLROnPlateau (factor=0.5, patience=3)
検証損失が頭打ちになった際に学習率を自動的に半減させる
Gradient Clippi
AI算出
技術分析ainew評価標準
深層学習モデルの設計やアテンション機構の説明可能性といった具体的な技術的知見が含まれているため、AI 関連度と検索機会は高いが、これは既存の AWS サービスを用いた導入事例・アーキテクチャ紹介であり、世界初の新規発表ではないため新規性は低め。また、日本固有の規制や企業事例に言及がないため日本関連性は低い。
6つの評価軸を見る
- AI関連度
- 75
- 情報源の信頼性
- 100
- 新規性
- 25
- 調べる価値
- 75
- 重複の少なさ
- 100
- 日本での有用性
- 25
関連記事
今日のまとめ
AIデイリーブリーフで今日の重要ニュースをまとめ読み