モデル署名の指定

モデルがどこで実行されても一貫したエクスペリエンスを保証するためには、Snowflake Model Registryがモデルの推論メソッドの入力スキーマと出力スキーマを把握しておく必要があります。つまり、入力または出力DataFrameのすべての列の名前と型です。これにより、これらの列は必要に応じてPythonとSQLのデータ型間でマッピングできるようになります。このスキーマは、関数の引数とその型になぞらえて*シグネチャ*と呼ばれています。署名には、温度設定など、推論動作を制御するオプションの*パラメーター*を含めることもできます。

ある種のMLフレームワークでは、モデルレジストリが、モデル自体のデータ構造から、あるいはサンプル入力データから、これらのスキーマを推測することができます。しかし、 NumPy 配列のような、この情報を持たないオブジェクトをモデルが受け取ったり返したりすることがよくあります。このような場合、Snowpark ML は、入力関数名を input_feature_1input_feature_2 などと推測します。同様に、出力機能には output_feature_1output_feature_2 などの名前が付けられています。

カスタムモデルでより意味のある名前を使うには、以下のいずれかを行います。

  • 通常はデータセットをpandasまたは Snowpark DataFrame に変換して、 sample_input_data を列名で更新します。

  • log_model に明示的に署名を渡します。モデルが出力に名前を生成しない場合、明示的なシグネチャが唯一の選択肢になる可能性があります。

シグネチャの推測

モデルレジストリ自体のように、シグネチャを自動的に生成することができます。snowflake.ml.model.model_signature.infer_signature を使って、提供されたサンプルの入力、出力、列名に基づいてシグネチャを推測し、以下の例のように、モデルをログに記録する際に適切なメソッドにそのシグネチャを適用します。

import pandas as pd
from sklearn import svm, datasets

from snowflake.ml.model import model_signature

digits = datasets.load_digits()
target_digit = 6

def one_vs_all(dataset, digit):
    return [x == digit for x in dataset]

train_features = digits.data[:10]
train_labels = one_vs_all(digits.target[:10], target_digit)
clf = svm.SVC(gamma=0.001, C=10.0, probability=True)
clf.fit(train_features, train_labels)

sig = model_signature.infer_signature(
    train_features,
    train_labels,
    input_feature_names=['column1', 'column2', ...],
    output_feature_names=['is_target_digit'])

# Supply a signature for every function the model exposes, in this case only `predict`.
mv = reg.log_model(
    clf,
    model_name='my_model',
    version_name='v1',
    signatures={"predict": sig}
)
Copy

この例では1つのメソッドだけにシグネチャを適用していますが、モデルが公開するメソッドごとにシグネチャを推測することができます。同じシグネチャを持つすべてのメソッドに、同じシグネチャオブジェクト(例では sig)を使うことができます。

注釈

Snowpark DataFrames の場合、 infer_signature は、 DataFrame のクエリを実行して、シグネチャが推論されるデータを取得する必要があります。データセットのサイズによっては、大きなコストがかかることもあります。ほとんどのトレーニングデータセットは、これを考慮するのに十分な大きさです。

このような大規模なクエリを回避するため、 infer_signature はクエリに LIMIT 100を追加することで、データの最初の100行のみを考慮します。しかし、これらの行がデータを代表していない場合は、推論されたシグネチャが不正確になる可能性があります。これは一般的に、データセットに多くの NULL 値が含まれてており、かつデータセットの特定の列の最初の100行が NULL 値のみである場合に発生します。この場合、推論されたシグネチャは、その列を誤って除外します。この問題を回避するには、次のセクションに示すようにシグネチャを明示的に提供します。

シグネチャの構築

snowflake.ml.model.model_signature.ModelSignature を使って手動でシグネチャを構築することもできます。スカラー型とテンソル型(ラグドテンソルを含む)の両方がサポートされています。

例:

from snowflake.ml.model.model_signature import ModelSignature, FeatureSpec, DataType

sig = ModelSignature(
    inputs=[
        FeatureSpec(dtype=DataType.DOUBLE, name=f_0),
        FeatureSpec(dtype=DataType.INT64, name=sparse_0_fixed_len, shape=(5, 5)),
        FeatureSpec(dtype=DataType.INT64, name=sparse_1_variable_len, shape=(-1,)),
    ],
    outputs=[
        FeatureSpec(dtype=DataType.FLOAT, name=output),
    ]
)
Copy

そして、そのシグネチャオブジェクト sig を、上記の例と同様に signatures 引数で log_model に渡し、適用するメソッドを指定します。

ParamSpecによるパラメーターの指定

モデルの署名には、入出力の特徴に加えて、*パラメーター*を含めることができます。パラメーターは、推論リクエストの際にモデル推論メソッドに渡すことができるオプションの構成値を定義します。処理対象のデータを指定する入力特徴とは異なり、パラメーターは、返す結果の数や温度設定など、推論動作を制御します。

パラメーターを定義するには、`snowflake.ml.model.model_signature.ModelSignature <https://docs.snowflake.com/developer-guide/snowpark-ml/reference/latest/api/model/snowflake.ml.model.model_signature.ModelSignature>`_の``ParamSpec``を使用します。

各``ParamSpec``には、名前、データ型、デフォルト値が必要です。デフォルト値は、推論時にパラメーターが明示的に指定されていない場合に使用されます。

パラメーターを含む署名の構築

以下の例では、入力/出力の特徴とパラメーターの両方を含むモデル署名を作成しています。

from snowflake.ml.model.model_signature import ModelSignature, FeatureSpec, ParamSpec, DataType

sig = ModelSignature(
    inputs=[
        FeatureSpec(dtype=DataType.STRING, name="input_text"),
    ],
    outputs=[
        FeatureSpec(dtype=DataType.STRING, name="output_text"),
    ],
    params=[
        ParamSpec(name="temperature", dtype=DataType.DOUBLE, default_value=0.7),
        ParamSpec(name="max_tokens", dtype=DataType.INT32, default_value=256),
    ]
)

mv = reg.log_model(
    my_model,
    model_name='my_model',
    version_name='v1',
    signatures={"predict": sig}
)
Copy

``infer_signature``で署名を推論するときに、パラメーターを含めることもできます。

from snowflake.ml.model.model_signature import ParamSpec, DataType
from snowflake.ml.model import model_signature

params = [
    ParamSpec(name="top_k", dtype=DataType.INT32, default_value=10),
    ParamSpec(name="threshold", dtype=DataType.DOUBLE, default_value=0.5),
]

sig = model_signature.infer_signature(
    input_data,
    output_data,
    params=params
)
Copy

注釈

パラメーター名は署名内で一意にする必要があり、入力特徴と同じ名前を付けることはできません。パラメーター名が入力特徴名と競合する場合は、``ValueError``が発生します。

``ParamSpec``引数の完全なリストについては、`APIリファレンス<https://docs.snowflake.com/developer-guide/snowpark-ml/reference/latest/model>`_をご参照ください。

推論時にパラメーター値を渡す方法の詳細については、:ref:`推論時のパラメーター受け渡し<label-inference-passing-params-python>`および:ref:`SQLSQLでのパラメーター受け渡し<label-inference-passing-params-sql>`をご参照ください。

データ型マッピング

このセクションでは、サポートされている型システムのSnowflakeモデルレジストリにおける型の等価性について説明します。

列データ型

次のテーブルは、モデル署名型、pandas DataFrames (NumPy)型、Snowpark Python型の等価性を示しています。

モデル署名型

pandas DataFrame(NumPy)型

Snowpark Python型

INT8

np.int8

ByteType

INT16

np.int16

ShortType

INT32

np.int32

IntegerType

INT64

np.int64

LongType

FLOAT

np.float32

FloatType

DOUBLE

np.float64

DoubleType

UINT8

np.uint8

ByteType

UINT16

np.uint16

ShortType

UINT32

np.uint32

IntegerType

UINT64

np.uint64

LongType

BOOL

np.bool_

BooleanType

STRING

np.str_

StringType

BYTES

np.bytes_

BinaryType

TIMESTAMP_NTZ

np.datetime64

TimestampType

形状が指定されたテンソル特徴の表現は、 np.object_ を使用します。

欠損値

モデルのシグネチャを推測するために sample_input_data を使用する場合、一般的に NULL の値を含んではいけません。モデルレジストリは提供されたデータからシグネチャーを推論しようとしますが、必ずしも完全に推論できるとは限りません。NULLs がサンプルデータに含まれないようにすることは、可能な限り、例えばデータ入力時など、できるだけ早い段階で行うのがよい方法です。

NumPyからの変換

NumPy データ型が 列データ型 で示される NumPy 型に安全にキャストできる場合、それは対応するデータ型として推論されます。

からの変換PyTorch

PyTorch型

モデル署名型

torch.uint8

UINT8

torch.int8

INT8

torch.int16

INT16

torch.int32

INT32

torch.int64

INT64

torch.float32

FLOAT

torch.float64

DOUBLE

torch.bool

BOOL

Snowparkからの変換

列データ型 に示すマッピングに加え、以下の変換が適用されます。

  • DecimalType を0の縮尺で INT64 をマッピングします。

  • DecimalType を0の値より大きい縮尺で DOUBLE をマッピングします。