Помогают защитить Большой Барьерный Риф с TensorFlow на Kaggle Присоединяйтесь вызов

Постройте линейную модель с помощью оценщиков

Посмотреть на TensorFlow.org Запускаем в Google Colab Посмотреть исходный код на GitHub Скачать блокнот

Обзор

Это конец к концу прохождения поезда модели логистической регрессии с использованием tf.estimator API. Модель часто используется в качестве основы для других, более сложных алгоритмов.

Настраивать

pip install sklearn
import os
import sys

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from IPython.display import clear_output
from six.moves import urllib

Загрузите набор данных titanic

Вы будете использовать набор данных Титаника с (довольно болезненной) целью прогнозирования выживаемости пассажиров с учетом таких характеристик, как пол, возраст, класс и т. Д.

import tensorflow.compat.v2.feature_column as fc

import tensorflow as tf
# Load dataset.
dftrain = pd.read_csv('https://storage.googleapis.com/tf-datasets/titanic/train.csv')
dfeval = pd.read_csv('https://storage.googleapis.com/tf-datasets/titanic/eval.csv')
y_train = dftrain.pop('survived')
y_eval = dfeval.pop('survived')

Изучите данные

Набор данных содержит следующие функции

dftrain.head()
dftrain.describe()

В обучающей и оценочной выборках 627 и 264 примера соответственно.

dftrain.shape[0], dfeval.shape[0]
(627, 264)

Большинство пассажиров - это люди в возрасте от 20 до 30 лет.

dftrain.age.hist(bins=20)
<AxesSubplot:>

PNG

На борту самолета пассажиров-мужчин примерно в два раза больше, чем пассажиров-женщин.

dftrain.sex.value_counts().plot(kind='barh')
<AxesSubplot:>

PNG

Большинство пассажиров находились в «третьем» классе.

dftrain['class'].value_counts().plot(kind='barh')
<AxesSubplot:>

PNG

У женщин гораздо больше шансов выжить, чем у мужчин. Это явно прогностическая особенность модели.

pd.concat([dftrain, y_train], axis=1).groupby('sex').survived.mean().plot(kind='barh').set_xlabel('% survive')
Text(0.5, 0, '% survive')

PNG

Разработка функций для модели

Оценщики используют систему функций столбцов , чтобы описать , как модель должна интерпретировать каждый из исходных функций ввода. Оценщик рассчитывает вектор числовых входов и функция столбец описывает как модель должна преобразовать каждую функцию.

Выбор и создание правильного набора столбцов функций - ключ к изучению эффективной модели. Столбец функции может быть либо одной из сырьевых материалов в оригинальных особенностях dict (столбец базовой функции), или любые новые столбцы созданы с помощью преобразований , определенных над одной или нескольких базовых столбцами (производном особенности столбцов).

Линейная оценка использует как числовые, так и категориальные функции. Столбцы функций работают со всеми оценщиками TensorFlow, и их цель - определить функции, используемые для моделирования. Кроме того, они предоставляют некоторые возможности разработки функций, такие как «горячее» кодирование, нормализация и разделение на сегменты.

Столбцы базовых характеристик

CATEGORICAL_COLUMNS = ['sex', 'n_siblings_spouses', 'parch', 'class', 'deck',
                       'embark_town', 'alone']
NUMERIC_COLUMNS = ['age', 'fare']

feature_columns = []
for feature_name in CATEGORICAL_COLUMNS:
  vocabulary = dftrain[feature_name].unique()
  feature_columns.append(tf.feature_column.categorical_column_with_vocabulary_list(feature_name, vocabulary))

for feature_name in NUMERIC_COLUMNS:
  feature_columns.append(tf.feature_column.numeric_column(feature_name, dtype=tf.float32))

В input_function определяет , каким образом данные преобразуются в tf.data.Dataset , который подает входной трубопровод в потоковом режиме. tf.data.Dataset может принимать в нескольких источниках , таких как dataframe, в CSV-формате файла, и многое другое.

def make_input_fn(data_df, label_df, num_epochs=10, shuffle=True, batch_size=32):
  def input_function():
    ds = tf.data.Dataset.from_tensor_slices((dict(data_df), label_df))
    if shuffle:
      ds = ds.shuffle(1000)
    ds = ds.batch(batch_size).repeat(num_epochs)
    return ds
  return input_function

train_input_fn = make_input_fn(dftrain, y_train)
eval_input_fn = make_input_fn(dfeval, y_eval, num_epochs=1, shuffle=False)

Вы можете проверить набор данных:

ds = make_input_fn(dftrain, y_train, batch_size=10)()
for feature_batch, label_batch in ds.take(1):
  print('Some feature keys:', list(feature_batch.keys()))
  print()
  print('A batch of class:', feature_batch['class'].numpy())
  print()
  print('A batch of Labels:', label_batch.numpy())
Some feature keys: ['sex', 'age', 'n_siblings_spouses', 'parch', 'fare', 'class', 'deck', 'embark_town', 'alone']

A batch of class: [b'Third' b'Third' b'Second' b'Third' b'First' b'First' b'Third' b'Third'
 b'Third' b'Third']

A batch of Labels: [0 1 0 1 1 0 0 0 1 1]

Вы также можете проверить результат определенного столбца признака , используя tf.keras.layers.DenseFeatures слой:

age_column = feature_columns[7]
tf.keras.layers.DenseFeatures([age_column])(feature_batch).numpy()
array([[ 9.  ],
       [24.  ],
       [23.  ],
       [28.  ],
       [24.  ],
       [40.  ],
       [31.  ],
       [36.  ],
       [28.  ],
       [ 0.75]], dtype=float32)

DenseFeatures принимает только плотные тензоры, чтобы проверить категорический столбец вам нужно преобразовать , что в колонку индикатора первый:

gender_column = feature_columns[0]
tf.keras.layers.DenseFeatures([tf.feature_column.indicator_column(gender_column)])(feature_batch).numpy()
array([[0., 1.],
       [0., 1.],
       [1., 0.],
       [0., 1.],
       [0., 1.],
       [1., 0.],
       [0., 1.],
       [1., 0.],
       [1., 0.],
       [0., 1.]], dtype=float32)

После добавления всех базовых функций к модели давайте обучим модель. Подготовка модели только одна команда с помощью tf.estimator API:

linear_est = tf.estimator.LinearClassifier(feature_columns=feature_columns)
linear_est.train(train_input_fn)
result = linear_est.evaluate(eval_input_fn)

clear_output()
print(result)
{'accuracy': 0.74242425, 'accuracy_baseline': 0.625, 'auc': 0.83409864, 'auc_precision_recall': 0.79196465, 'average_loss': 0.48227197, 'label/mean': 0.375, 'loss': 0.47621801, 'precision': 0.64761907, 'prediction/mean': 0.4210519, 'recall': 0.68686867, 'global_step': 200}

Столбцы производных функций

Теперь вы достигли точности 75%. Использование каждого столбца базовых характеристик по отдельности может оказаться недостаточным для объяснения данных. Например, корреляция между возрастом и ярлыком может быть разной для разного пола. Поэтому, если вы только узнаете один вес модели для gender="Male" и gender="Female" , вы не будете захватывать каждый половозрастной комбинации (например , различая gender="Male" И age="30" И gender="Male" И age="40" ).

Чтобы узнать разницу между различными комбинациями функции вы можете добавить скрещенные столбцы функций модели (вы можете также bucketize возраст колонки перед Крестом колонки):

age_x_gender = tf.feature_column.crossed_column(['age', 'sex'], hash_bucket_size=100)

После добавления функции комбинирования в модель давайте снова обучим модель:

derived_feature_columns = [age_x_gender]
linear_est = tf.estimator.LinearClassifier(feature_columns=feature_columns+derived_feature_columns)
linear_est.train(train_input_fn)
result = linear_est.evaluate(eval_input_fn)

clear_output()
print(result)
{'accuracy': 0.7689394, 'accuracy_baseline': 0.625, 'auc': 0.8474442, 'auc_precision_recall': 0.7786934, 'average_loss': 0.4796637, 'label/mean': 0.375, 'loss': 0.47112098, 'precision': 0.73170733, 'prediction/mean': 0.3178967, 'recall': 0.6060606, 'global_step': 200}

Теперь он достигает точности 77,6%, что немного лучше, чем при обучении только базовым функциям. Вы можете попробовать использовать больше функций и преобразований, чтобы увидеть, сможете ли вы добиться большего!

Теперь вы можете использовать модель поезда, чтобы делать прогнозы для пассажира на основе оценочного набора. Модели TensorFlow оптимизированы для одновременного прогнозирования пакета или коллекции примеров. Ранее eval_input_fn была определена с использованием всего набора оценки.

pred_dicts = list(linear_est.predict(eval_input_fn))
probs = pd.Series([pred['probabilities'][1] for pred in pred_dicts])

probs.plot(kind='hist', bins=20, title='predicted probabilities')
INFO:tensorflow:Calling model_fn.
INFO:tensorflow:Done calling model_fn.
INFO:tensorflow:Graph was finalized.
INFO:tensorflow:Restoring parameters from /tmp/tmpoq0ukjec/model.ckpt-200
INFO:tensorflow:Running local_init_op.
INFO:tensorflow:Done running local_init_op.
<AxesSubplot:title={'center':'predicted probabilities'}, ylabel='Frequency'>

PNG

Наконец, взгляните на рабочую характеристику приемника (ROC) результатов, которая даст нам лучшее представление о компромиссе между истинно положительной частотой и ложноположительной частотой.

from sklearn.metrics import roc_curve
from matplotlib import pyplot as plt

fpr, tpr, _ = roc_curve(y_eval, probs)
plt.plot(fpr, tpr)
plt.title('ROC curve')
plt.xlabel('false positive rate')
plt.ylabel('true positive rate')
plt.xlim(0,)
plt.ylim(0,)
(0.0, 1.05)

PNG