Cette page a été traduite par l'API Cloud Translation.
Switch to English

Estimateurs en conserve sur treillis TF

Voir sur TensorFlow.org Exécuter dans Google Colab Afficher la source sur GitHub Télécharger le carnet

Aperçu

Les estimateurs en conserve sont des moyens rapides et faciles de former des modèles TFL pour des cas d'utilisation typiques. Ce guide décrit les étapes nécessaires pour créer un estimateur prédéfini TFL.

Installer

Installation du package TF Lattice:

pip install -q tensorflow-lattice

Importation des packages requis:

import tensorflow as tf

import copy
import logging
import numpy as np
import pandas as pd
import sys
import tensorflow_lattice as tfl
from tensorflow import feature_column as fc
logging.disable(sys.maxsize)

Téléchargement du jeu de données UCI Statlog (Heart):

csv_file = tf.keras.utils.get_file(
    'heart.csv', 'http://storage.googleapis.com/applied-dl/heart.csv')
df = pd.read_csv(csv_file)
target = df.pop('target')
train_size = int(len(df) * 0.8)
train_x = df[:train_size]
train_y = target[:train_size]
test_x = df[train_size:]
test_y = target[train_size:]
df.head()

Définition des valeurs par défaut utilisées pour la formation dans ce guide:

LEARNING_RATE = 0.01
BATCH_SIZE = 128
NUM_EPOCHS = 500
PREFITTING_NUM_EPOCHS = 10

Colonnes de caractéristiques

Comme pour tout autre estimateur TF, les données doivent être transmises à l'estimateur, qui est généralement via un input_fn et analysées à l'aide de FeatureColumns .

# Feature columns.
# - age
# - sex
# - cp        chest pain type (4 values)
# - trestbps  resting blood pressure
# - chol      serum cholestoral in mg/dl
# - fbs       fasting blood sugar > 120 mg/dl
# - restecg   resting electrocardiographic results (values 0,1,2)
# - thalach   maximum heart rate achieved
# - exang     exercise induced angina
# - oldpeak   ST depression induced by exercise relative to rest
# - slope     the slope of the peak exercise ST segment
# - ca        number of major vessels (0-3) colored by flourosopy
# - thal      3 = normal; 6 = fixed defect; 7 = reversable defect
feature_columns = [
    fc.numeric_column('age', default_value=-1),
    fc.categorical_column_with_vocabulary_list('sex', [0, 1]),
    fc.numeric_column('cp'),
    fc.numeric_column('trestbps', default_value=-1),
    fc.numeric_column('chol'),
    fc.categorical_column_with_vocabulary_list('fbs', [0, 1]),
    fc.categorical_column_with_vocabulary_list('restecg', [0, 1, 2]),
    fc.numeric_column('thalach'),
    fc.categorical_column_with_vocabulary_list('exang', [0, 1]),
    fc.numeric_column('oldpeak'),
    fc.categorical_column_with_vocabulary_list('slope', [0, 1, 2]),
    fc.numeric_column('ca'),
    fc.categorical_column_with_vocabulary_list(
        'thal', ['normal', 'fixed', 'reversible']),
]

Les estimateurs prédéfinis TFL utilisent le type de colonne d'entités pour décider du type de couche d'étalonnage à utiliser. Nous utilisons une couche tfl.layers.PWLCalibration pour les colonnes d' tfl.layers.PWLCalibration numériques et une couche tfl.layers.PWLCalibration pour les colonnes d' tfl.layers.CategoricalCalibration catégorielles.

Notez que les colonnes d'entités catégorielles ne sont pas encapsulées par une colonne d'entités d'incorporation. Ils sont directement introduits dans l'estimateur.

Création de input_fn

Comme pour tout autre estimateur, vous pouvez utiliser un input_fn pour fournir des données au modèle à des fins d'apprentissage et d'évaluation. Les estimateurs TFL peuvent calculer automatiquement les quantiles des entités et les utiliser comme points-clés d'entrée pour la couche d'étalonnage PWL. Pour ce faire, ils nécessitent de passer un feature_analysis_input_fn , qui est similaire à l'entraînement input_fn mais avec une seule époque ou un sous-échantillon des données.

train_input_fn = tf.compat.v1.estimator.inputs.pandas_input_fn(
    x=train_x,
    y=train_y,
    shuffle=False,
    batch_size=BATCH_SIZE,
    num_epochs=NUM_EPOCHS,
    num_threads=1)

# feature_analysis_input_fn is used to collect statistics about the input.
feature_analysis_input_fn = tf.compat.v1.estimator.inputs.pandas_input_fn(
    x=train_x,
    y=train_y,
    shuffle=False,
    batch_size=BATCH_SIZE,
    # Note that we only need one pass over the data.
    num_epochs=1,
    num_threads=1)

test_input_fn = tf.compat.v1.estimator.inputs.pandas_input_fn(
    x=test_x,
    y=test_y,
    shuffle=False,
    batch_size=BATCH_SIZE,
    num_epochs=1,
    num_threads=1)

# Serving input fn is used to create saved models.
serving_input_fn = (
    tf.estimator.export.build_parsing_serving_input_receiver_fn(
        feature_spec=fc.make_parse_example_spec(feature_columns)))

Configurations de fonctionnalités

L'étalonnage des fonctionnalités et les configurations par fonctionnalité sont définis à l'aide de tfl.configs.FeatureConfig . Les configurations d'entités incluent les contraintes de monotonie, la régularisation par tfl.configs.RegularizerConfig (voir tfl.configs.RegularizerConfig ) et les tailles de réseau pour les modèles de réseau.

Si aucune configuration n'est définie pour une fonction d'entrée, la configuration par défaut dans tfl.config.FeatureConfig est utilisée.

# Feature configs are used to specify how each feature is calibrated and used.
feature_configs = [
    tfl.configs.FeatureConfig(
        name='age',
        lattice_size=3,
        # By default, input keypoints of pwl are quantiles of the feature.
        pwl_calibration_num_keypoints=5,
        monotonicity='increasing',
        pwl_calibration_clip_max=100,
        # Per feature regularization.
        regularizer_configs=[
            tfl.configs.RegularizerConfig(name='calib_wrinkle', l2=0.1),
        ],
    ),
    tfl.configs.FeatureConfig(
        name='cp',
        pwl_calibration_num_keypoints=4,
        # Keypoints can be uniformly spaced.
        pwl_calibration_input_keypoints='uniform',
        monotonicity='increasing',
    ),
    tfl.configs.FeatureConfig(
        name='chol',
        # Explicit input keypoint initialization.
        pwl_calibration_input_keypoints=[126.0, 210.0, 247.0, 286.0, 564.0],
        monotonicity='increasing',
        # Calibration can be forced to span the full output range by clamping.
        pwl_calibration_clamp_min=True,
        pwl_calibration_clamp_max=True,
        # Per feature regularization.
        regularizer_configs=[
            tfl.configs.RegularizerConfig(name='calib_hessian', l2=1e-4),
        ],
    ),
    tfl.configs.FeatureConfig(
        name='fbs',
        # Partial monotonicity: output(0) <= output(1)
        monotonicity=[(0, 1)],
    ),
    tfl.configs.FeatureConfig(
        name='trestbps',
        pwl_calibration_num_keypoints=5,
        monotonicity='decreasing',
    ),
    tfl.configs.FeatureConfig(
        name='thalach',
        pwl_calibration_num_keypoints=5,
        monotonicity='decreasing',
    ),
    tfl.configs.FeatureConfig(
        name='restecg',
        # Partial monotonicity: output(0) <= output(1), output(0) <= output(2)
        monotonicity=[(0, 1), (0, 2)],
    ),
    tfl.configs.FeatureConfig(
        name='exang',
        # Partial monotonicity: output(0) <= output(1)
        monotonicity=[(0, 1)],
    ),
    tfl.configs.FeatureConfig(
        name='oldpeak',
        pwl_calibration_num_keypoints=5,
        monotonicity='increasing',
    ),
    tfl.configs.FeatureConfig(
        name='slope',
        # Partial monotonicity: output(0) <= output(1), output(1) <= output(2)
        monotonicity=[(0, 1), (1, 2)],
    ),
    tfl.configs.FeatureConfig(
        name='ca',
        pwl_calibration_num_keypoints=4,
        monotonicity='increasing',
    ),
    tfl.configs.FeatureConfig(
        name='thal',
        # Partial monotonicity:
        # output(normal) <= output(fixed)
        # output(normal) <= output(reversible)        
        monotonicity=[('normal', 'fixed'), ('normal', 'reversible')],
    ),
]

Modèle linéaire calibré

Pour construire un estimateur tfl.configs TFL, construisez une configuration de modèle à partir de tfl.configs . Un modèle linéaire calibré est construit à l'aide de tfl.configs.CalibratedLinearConfig . Il applique un étalonnage linéaire et catégoriel par morceaux sur les entités d'entrée, suivi d'une combinaison linéaire et d'un étalonnage linéaire par morceaux en sortie en option. Lors de l'utilisation de l'étalonnage de sortie ou lorsque des limites de sortie sont spécifiées, la couche linéaire appliquera une moyenne pondérée aux entrées étalonnées.

Cet exemple crée un modèle linéaire calibré sur les 5 premières entités. Nous utilisons tfl.visualization pour tracer le graphe du modèle avec les tracés du calibrateur.

# Model config defines the model structure for the estimator.
model_config = tfl.configs.CalibratedLinearConfig(
    feature_configs=feature_configs,
    use_bias=True,
    output_calibration=True,
    regularizer_configs=[
        # Regularizer for the output calibrator.
        tfl.configs.RegularizerConfig(name='output_calib_hessian', l2=1e-4),
    ])
# A CannedClassifier is constructed from the given model config.
estimator = tfl.estimators.CannedClassifier(
    feature_columns=feature_columns[:5],
    model_config=model_config,
    feature_analysis_input_fn=feature_analysis_input_fn,
    optimizer=tf.keras.optimizers.Adam(LEARNING_RATE),
    config=tf.estimator.RunConfig(tf_random_seed=42))
estimator.train(input_fn=train_input_fn)
results = estimator.evaluate(input_fn=test_input_fn)
print('Calibrated linear test AUC: {}'.format(results['auc']))
saved_model_path = estimator.export_saved_model(estimator.model_dir,
                                                serving_input_fn)
model_graph = tfl.estimators.get_model_graph(saved_model_path)
tfl.visualization.draw_model_graph(model_graph)
Calibrated linear test AUC: 0.834586501121521

png

Modèle de treillis calibré

Un modèle de réseau calibré est construit à l'aide de tfl.configs.CalibratedLatticeConfig . Un modèle de réseau étalonné applique un étalonnage linéaire par morceaux et catégoriel sur les entités d'entrée, suivi d'un modèle de réseau et d'un étalonnage linéaire par morceaux en sortie facultatif.

Cet exemple crée un modèle de réseau calibré sur les 5 premières entités.

# This is calibrated lattice model: Inputs are calibrated, then combined
# non-linearly using a lattice layer.
model_config = tfl.configs.CalibratedLatticeConfig(
    feature_configs=feature_configs,
    regularizer_configs=[
        # Torsion regularizer applied to the lattice to make it more linear.
        tfl.configs.RegularizerConfig(name='torsion', l2=1e-4),
        # Globally defined calibration regularizer is applied to all features.
        tfl.configs.RegularizerConfig(name='calib_hessian', l2=1e-4),
    ])
# A CannedClassifier is constructed from the given model config.
estimator = tfl.estimators.CannedClassifier(
    feature_columns=feature_columns[:5],
    model_config=model_config,
    feature_analysis_input_fn=feature_analysis_input_fn,
    optimizer=tf.keras.optimizers.Adam(LEARNING_RATE),
    config=tf.estimator.RunConfig(tf_random_seed=42))
estimator.train(input_fn=train_input_fn)
results = estimator.evaluate(input_fn=test_input_fn)
print('Calibrated lattice test AUC: {}'.format(results['auc']))
saved_model_path = estimator.export_saved_model(estimator.model_dir,
                                                serving_input_fn)
model_graph = tfl.estimators.get_model_graph(saved_model_path)
tfl.visualization.draw_model_graph(model_graph)
Calibrated lattice test AUC: 0.8433583974838257

png

Ensemble de treillis calibré

Lorsque le nombre d'entités est important, vous pouvez utiliser un modèle d'ensemble, qui crée plusieurs treillis plus petits pour des sous-ensembles d'entités et fait la moyenne de leur sortie au lieu de créer un seul grand treillis. Les modèles de réseau d'ensemble sont construits à l'aide de tfl.configs.CalibratedLatticeEnsembleConfig . Un modèle d'ensemble de réseau étalonné applique un étalonnage linéaire par morceaux et catégoriel à l'entité d'entrée, suivi d'un ensemble de modèles de réseau et d'un étalonnage linéaire par morceaux en sortie facultatif.

Ensemble de treillis aléatoire

La configuration de modèle suivante utilise un sous-ensemble aléatoire de fonctionnalités pour chaque treillis.

# This is random lattice ensemble model with separate calibration:
# model output is the average output of separately calibrated lattices.
model_config = tfl.configs.CalibratedLatticeEnsembleConfig(
    feature_configs=feature_configs,
    num_lattices=5,
    lattice_rank=3)
# A CannedClassifier is constructed from the given model config.
estimator = tfl.estimators.CannedClassifier(
    feature_columns=feature_columns,
    model_config=model_config,
    feature_analysis_input_fn=feature_analysis_input_fn,
    optimizer=tf.keras.optimizers.Adam(LEARNING_RATE),
    config=tf.estimator.RunConfig(tf_random_seed=42))
estimator.train(input_fn=train_input_fn)
results = estimator.evaluate(input_fn=test_input_fn)
print('Random ensemble test AUC: {}'.format(results['auc']))
saved_model_path = estimator.export_saved_model(estimator.model_dir,
                                                serving_input_fn)
model_graph = tfl.estimators.get_model_graph(saved_model_path)
tfl.visualization.draw_model_graph(model_graph, calibrator_dpi=15)
Random ensemble test AUC: 0.8991228342056274

png

Ensemble de treillis aléatoire de couche RTL

La configuration de modèle suivante utilise une couche tfl.layers.RTL qui utilise un sous-ensemble aléatoire d'entités pour chaque treillis. Nous notons que tfl.layers.RTL ne prend en charge que les contraintes de monotonie et doit avoir la même taille de réseau pour toutes les entités et aucune régularisation par entité. Notez que l'utilisation d'un calque tfl.layers.RTL vous permet de mettre à l'échelle des ensembles beaucoup plus grands que d'utiliser des instances tfl.layers.Lattice séparées.

# Make sure our feature configs have the same lattice size, no per-feature
# regularization, and only monotonicity constraints.
rtl_layer_feature_configs = copy.deepcopy(feature_configs)
for feature_config in rtl_layer_feature_configs:
  feature_config.lattice_size = 2
  feature_config.unimodality = 'none'
  feature_config.reflects_trust_in = None
  feature_config.dominates = None
  feature_config.regularizer_configs = None
# This is RTL layer ensemble model with separate calibration:
# model output is the average output of separately calibrated lattices.
model_config = tfl.configs.CalibratedLatticeEnsembleConfig(
    lattices='rtl_layer',
    feature_configs=rtl_layer_feature_configs,
    num_lattices=5,
    lattice_rank=3)
# A CannedClassifier is constructed from the given model config.
estimator = tfl.estimators.CannedClassifier(
    feature_columns=feature_columns,
    model_config=model_config,
    feature_analysis_input_fn=feature_analysis_input_fn,
    optimizer=tf.keras.optimizers.Adam(LEARNING_RATE),
    config=tf.estimator.RunConfig(tf_random_seed=42))
estimator.train(input_fn=train_input_fn)
results = estimator.evaluate(input_fn=test_input_fn)
print('Random ensemble test AUC: {}'.format(results['auc']))
saved_model_path = estimator.export_saved_model(estimator.model_dir,
                                                serving_input_fn)
model_graph = tfl.estimators.get_model_graph(saved_model_path)
tfl.visualization.draw_model_graph(model_graph, calibrator_dpi=15)
Random ensemble test AUC: 0.9241854548454285

png

Ensemble de treillis de cristaux

TFL fournit également un algorithme de disposition des fonctionnalités heuristique, appelé Crystals . L'algorithme Crystals entraîne d'abord un modèle de pré - ajustement qui estime les interactions de caractéristiques par paires. Il organise ensuite l'ensemble final de telle sorte que les entités avec plus d'interactions non linéaires soient dans les mêmes réseaux.

Pour les modèles Crystals, vous devrez également fournir un prefitting_input_fn qui est utilisé pour entraîner le modèle de prefitting, comme décrit ci-dessus. Le modèle de pré-montage n'a pas besoin d'être entièrement formé, donc quelques époques devraient suffire.

prefitting_input_fn = tf.compat.v1.estimator.inputs.pandas_input_fn(
    x=train_x,
    y=train_y,
    shuffle=False,
    batch_size=BATCH_SIZE,
    num_epochs=PREFITTING_NUM_EPOCHS,
    num_threads=1)

Vous pouvez ensuite créer un modèle Crystal en définissant lattice='crystals' dans la configuration du modèle.

# This is Crystals ensemble model with separate calibration: model output is
# the average output of separately calibrated lattices.
model_config = tfl.configs.CalibratedLatticeEnsembleConfig(
    feature_configs=feature_configs,
    lattices='crystals',
    num_lattices=5,
    lattice_rank=3)
# A CannedClassifier is constructed from the given model config.
estimator = tfl.estimators.CannedClassifier(
    feature_columns=feature_columns,
    model_config=model_config,
    feature_analysis_input_fn=feature_analysis_input_fn,
    # prefitting_input_fn is required to train the prefitting model.
    prefitting_input_fn=prefitting_input_fn,
    optimizer=tf.keras.optimizers.Adam(LEARNING_RATE),
    prefitting_optimizer=tf.keras.optimizers.Adam(LEARNING_RATE),
    config=tf.estimator.RunConfig(tf_random_seed=42))
estimator.train(input_fn=train_input_fn)
results = estimator.evaluate(input_fn=test_input_fn)
print('Crystals ensemble test AUC: {}'.format(results['auc']))
saved_model_path = estimator.export_saved_model(estimator.model_dir,
                                                serving_input_fn)
model_graph = tfl.estimators.get_model_graph(saved_model_path)
tfl.visualization.draw_model_graph(model_graph, calibrator_dpi=15)
Crystals ensemble test AUC: 0.8853383660316467

png

Vous pouvez tracer des calibrateurs d' tfl.visualization avec plus de détails à l'aide du module tfl.visualization .

_ = tfl.visualization.plot_feature_calibrator(model_graph, "age")
_ = tfl.visualization.plot_feature_calibrator(model_graph, "restecg")

png

png