Integrando MinDiff com MinDiffModel

Introdução

Existem duas etapas para integrar o MinDiff em seu modelo:

  1. Prepare os dados (coberto no guia de preparação de entrada ).

  2. Altere ou crie um modelo que integre o MinDiff durante o treinamento.

Este guia irá cobrir a forma mais simples de completar o segundo passo: usando MinDiffModel .

Configurar

pip install -q --upgrade tensorflow-model-remediation
import tensorflow as tf
tf.get_logger().setLevel('ERROR')  # Avoid TF warnings.
from tensorflow_model_remediation import min_diff
from tensorflow_model_remediation.tools.tutorials_utils import uci as tutorials_utils

Primeiro, baixe os dados. Para concisão, a lógica de entrada preparação foi fatoramos em funções auxiliares como descrito no guia de preparação de entrada . Você pode ler o guia completo para obter detalhes sobre este processo.

# Original DataFrame for training, sampled at 0.3 for reduced runtimes.
train_df = tutorials_utils.get_uci_data(split='train', sample=0.3)

# Dataset needed to train with MinDiff.
train_with_min_diff_ds = (
    tutorials_utils.get_uci_with_min_diff_dataset(split='train', sample=0.3))

Modelo Original

Este guia usa um básico, untuned keras.Model usando a API funcional para destacar usando MinDiff. Em um aplicativo do mundo real, você escolheria cuidadosamente a arquitetura do modelo e usaria o ajuste para melhorar a qualidade do modelo antes de tentar resolver quaisquer problemas de imparcialidade.

Desde MinDiffModel é projetado para trabalhar com a maioria dos Keras Model aulas, temos consignado a lógica de construir o modelo em uma função auxiliar: get_uci_model .

Treinamento com um DataFrame Pandas

Este guia treina em uma única época para velocidade, mas pode melhorar facilmente o desempenho do modelo aumentando o número de épocas.

model = tutorials_utils.get_uci_model()

model.compile(optimizer='adam', loss='binary_crossentropy')

df_without_target = train_df.drop(['target'], axis=1)  # Drop 'target' for x.
_ = model.fit(
    x=dict(df_without_target),  # The model expects a dictionary of features.
    y=train_df['target'],
    batch_size=128,
    epochs=1)
77/77 [==============================] - 3s 23ms/step - loss: 0.8589

Treinar com um tf.data.Dataset

A formação equivalente com um tf.data.Dataset ficaria muito semelhante (embora inicialização e aleatoriedade de entrada pode originar resultados ligeiramente diferentes).

model = tutorials_utils.get_uci_model()

model.compile(optimizer='adam', loss='binary_crossentropy')

_ = model.fit(
    tutorials_utils.df_to_dataset(train_df, batch_size=128),  # Converted to Dataset.
    epochs=1)
77/77 [==============================] - 3s 23ms/step - loss: 0.6416

Integrando MinDiff para treinamento

Depois que os dados estiverem preparados, aplique MinDiff ao seu modelo com as seguintes etapas:

  1. Crie o modelo original como faria sem MinDiff.
original_model = tutorials_utils.get_uci_model()
  1. Envolvê-la em um MinDiffModel .
min_diff_model = min_diff.keras.MinDiffModel(
    original_model=original_model,
    loss=min_diff.losses.MMDLoss(),
    loss_weight=1)
  1. Compile-o como faria sem MinDiff.
min_diff_model.compile(optimizer='adam', loss='binary_crossentropy')
  1. Treiná-lo com o conjunto de dados MinDiff ( train_with_min_diff_ds neste caso).
_ = min_diff_model.fit(train_with_min_diff_ds, epochs=1)
77/77 [==============================] - 6s 31ms/step - loss: 0.7883 - min_diff_loss: 0.0379

Avaliação e Previsão com MinDiffModel

Ambos avaliar e prever com um MinDiffModel são semelhantes a fazê-lo com o modelo original.

Ao ligar para evaluate você pode passar em qualquer conjunto de dados original ou o que contém dados MinDiff. Se você escolher o último, você também terá a min_diff_loss métrica para além de quaisquer outras métricas sendo medido loss também incluirá a min_diff_loss .

Ao ligar para evaluate você pode passar em qualquer conjunto de dados original ou o que contém dados MinDiff. Se você incluir MinDiff na chamada para avaliar, duas coisas serão diferentes:

  • Uma métrica adicional chamado min_diff_loss estará presente na saída.
  • O valor da loss métrica será a soma do original loss métrica (não mostrado na saída) eo min_diff_loss .
_ = min_diff_model.evaluate(
    tutorials_utils.df_to_dataset(train_df, batch_size=128))
# Calling with MinDiff data will include min_diff_loss in metrics.
_ = min_diff_model.evaluate(train_with_min_diff_ds)
77/77 [==============================] - 2s 22ms/step - loss: 0.4638
77/77 [==============================] - 3s 32ms/step - loss: 0.5087 - min_diff_loss: 0.0451

Ao ligar para predict você pode tecnicamente também passar no conjunto de dados com os dados MinDiff mas serão ignorados e não afetam a saída.

_ = min_diff_model.predict(
    tutorials_utils.df_to_dataset(train_df, batch_size=128))
_ = min_diff_model.predict(train_with_min_diff_ds)  # Identical to results above.

As limitações da utilização MinDiffModel directamente

Ao usar MinDiffModel como descrito acima, a maioria dos métodos irá utilizar as implementações padrão de tf.keras.Model (exceções listadas na documentação da API ).

print('MinDiffModel.fit == keras.Model.fit')
print(min_diff.keras.MinDiffModel.fit == tf.keras.Model.fit)
print('MinDiffModel.train_step == keras.Model.train_step')
print(min_diff.keras.MinDiffModel.train_step == tf.keras.Model.train_step)
MinDiffModel.fit == keras.Model.fit
True
MinDiffModel.train_step == keras.Model.train_step
True

Para keras.Sequential ou keras.Model , isso é perfeitamente bem desde que eles usam as mesmas funções.

print('Sequential.fit == keras.Model.fit')
print(tf.keras.Sequential.fit == tf.keras.Model.fit)
print('tf.keras.Sequential.train_step == keras.Model.train_step')
print(tf.keras.Sequential.train_step == tf.keras.Model.train_step)
Sequential.fit == keras.Model.fit
True
tf.keras.Sequential.train_step == keras.Model.train_step
True

No entanto, se o seu modelo é uma subclasse de keras.Model , envolvendo-o com MinDiffModel vai efetivamente perder a personalização.

class CustomModel(tf.keras.Model):

  def train_step(self, **kwargs):
    pass  # Custom implementation.

print('CustomModel.train_step == keras.Model.train_step')
print(CustomModel.train_step == tf.keras.Model.train_step)
CustomModel.train_step == keras.Model.train_step
False

Se este é seu caso de uso, você não deve usar MinDiffModel diretamente. Em vez disso, você precisará subclasse-lo conforme descrito no guia de personalização .

Recursos adicionais