sklearn.externals.joblib インポートエラーの解決方法
問題の概要
scikit-learn (sklearn) を使用している際に、以下のようなインポートエラーが発生することがあります:
from sklearn.externals import joblib
# ImportError: cannot import name 'joblib' from 'sklearn.externals'
また、直接 import joblib
を試みた場合でも、保存されたモデルファイルの読み込み時に次のエラーが発生することがあります:
ModuleNotFoundError: No module named 'sklearn.externals.joblib'
問題の原因
この問題は、scikit-learn のバージョン移行に伴う変更が原因です。scikit-learn 0.21 以降、sklearn.externals.joblib
は非推奨 (deprecated) となり、バージョン 0.23 で完全に削除されました。
歴史的背景
かつて scikit-learn は内部で joblib を使用しており、sklearn.externals.joblib
経由でアクセスできましたが、現在は独立したパッケージとして扱うことが推奨されています。
解決方法
方法1: 直接 joblib をインポートする(推奨)
最も簡単な解決方法は、インポート文を変更することです:
# 変更前
from sklearn.externals import joblib
# 変更後
import joblib
方法2: joblib のインストール
joblib がインストールされていない場合は、以下のコマンドでインストールしてください:
pip install joblib
conda install joblib
方法3: 古いモデルファイルの変換
既存のモデルファイルが古い形式で保存されている場合は、一時的に古いバージョンの scikit-learn を使用して変換する必要があります:
- 古い環境の設定:
pip install scikit-learn==0.22.2 # またはモデル作成時のバージョン
- モデルの変換スクリプト:
import sklearn.externals.joblib as extjoblib
import joblib
# 古い形式でモデルを読み込み
model = extjoblib.load('old_model.pkl')
# 新しい形式で保存
joblib.dump(model, 'new_model.pkl')
- 最新の環境に戻り、変換後のモデルを使用:
import joblib
model = joblib.load('new_model.pkl')
コード例
以下は、修正後の適切なコード例です:
import pandas as pd
import numpy as np
import joblib # sklearn.externals ではなく直接インポート
# ... 他のインポート
ENV = 'dev'
model_d2v = load_d2v('model_d2v_version_002', ENV)
def load_d2v(fname, env):
model_name = fname
if env == 'dev':
try:
model = joblib.load(model_name) # 直接 joblib を使用
except:
s3_base_path = 's3://sd-flikku/datalake/doc2vec_model'
path = s3_base_path + '/' + model_name
command = f"aws s3 cp {path} {model_name}".split()
print('loading...' + model_name)
subprocess.call(command)
model = joblib.load(model_name) # 直接 joblib を使用
else:
s3_base_path = 's3://sd-flikku/datalake/doc2vec_model'
path = s3_base_path + '/' + model_name
command = f"aws s3 cp {path} {model_name}".split()
print('loading...' + model_name)
subprocess.call(command)
model = joblib.load(model_name) # 直接 joblib を使用
return model
注意点
- バージョン 0.23 以降の scikit-learn では
sklearn.externals.joblib
は完全に削除されています - 新しいプロジェクトでは常に
import joblib
を使用してください - チームで開発している場合は、すべてのメンバーが同じアプローチを使用するようにしてください
参考情報
ヒント
モデル永続化には、最近では pickle 形式よりも ONNX 形式やモデル固有の保存形式を使用することが推奨される場合もあります。プロジェクトの要件に応じて適切な形式を選択してください。
この問題はインポート文を変更するだけで解決できる場合がほとんどですが、古いモデルファイルを扱っている場合は追加の変換作業が必要になることがあります。