Предыдущий ‹‹ Матрица путаницы и дисбаланс данных (2/3)

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

Визуализация данных

Мы еще раз воспользуемся набором данных с разными классами объектов, найденных на горе:

import pandas
import numpy
!wget https://raw.githubusercontent.com/MicrosoftDocs/mslearn-introduction-to-machine-learning/main/graphing.py
!wget https://raw.githubusercontent.com/MicrosoftDocs/mslearn-introduction-to-machine-learning/main/Data/snow_objects.csv

#Import the data from the .csv file
dataset = pandas.read_csv('snow_objects.csv', delimiter="\t")

#Let's have a look at the data
dataset
           size     roughness     color     motion     label
0       50.959361    1.318226     green    0.054290    tree
1       60.008521    0.554291     brown    0.000000    tree
2       20.530772    1.097752     white    1.380464    tree
3       28.092138    0.966482     grey     0.650528    tree
4       48.344211    0.799093     grey     0.000000    tree
 ...       ...          ...        ...        ...       ...
2195    1.918175     1.182234     white    0.000000    animal
2196    1.000694     1.332152     black    4.041097    animal
2197    2.331485     0.734561     brown    0.961486    animal
2198    1.786560     0.707935     black    0.000000    animal
2199    1.518813     1.447957     brown    0.000000    animal

2200 rows × 5 columns

Напомним, что чтобы использовать приведенный выше набор данных для двоичной классификации, нам нужно добавить в наш набор данных еще один столбец и установить для него значение true, где исходная метка — путешественник и false для чего-либо еще:

Затем давайте добавим эту метку, разделим набор данных и снова обучим модель:

from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import train_test_split

# Add a new label with true/false values to our dataset
dataset["is_hiker"] = dataset.label == "hiker"

# Split the dataset in an 70/30 train/test ratio. 
train, test = train_test_split(dataset, test_size=0.3, random_state=1, shuffle=True)

# define a random forest model
model = RandomForestClassifier(n_estimators=1, random_state=1, verbose=False)

# Define which features are to be used 
features = ["size", "roughness", "motion"]

# Train the model using the binary label
model.fit(train[features], train.is_hiker)

print("Model trained!")
Model trained!

Теперь мы можем использовать эту модель, чтобы предсказать, являются ли объекты на снегу путешественниками или нет. Давайте построим матрицу путаницы:

# sklearn has a very convenient utility to build confusion matrices
from sklearn.metrics import confusion_matrix
import plotly.figure_factory as ff

# Calculate the model's accuracy on the TEST set
actual = test.is_hiker
predictions = model.predict(test[features])

# Build and print our confusion matrix, using the actual values and predictions 
# from the test set, calculated in previous cells
cm = confusion_matrix(actual, predictions, normalize=None)

# Create the list of unique labels in the test set, to use in our plot
# I.e., ['True', 'False',]
unique_targets = sorted(list(test["is_hiker"].unique()))

# Convert values to lower case so the plot code can count the outcomes
x = y = [str(s).lower() for s in unique_targets]

# Plot the matrix above as a heatmap with annotations (values) in its cells
fig = ff.create_annotated_heatmap(cm, x, y)

# Set titles and ordering
fig.update_layout(  title_text="<b>Confusion matrix</b>", 
                    yaxis = dict(categoryorder = "category descending"))

fig.add_annotation(dict(font=dict(color="black",size=14),
                        x=0.5,
                        y=-0.15,
                        showarrow=False,
                        text="Predicted label",
                        xref="paper",
                        yref="paper"))

fig.add_annotation(dict(font=dict(color="black",size=14),
                        x=-0.15,
                        y=0.5,
                        showarrow=False,
                        text="Actual label",
                        textangle=-90,
                        xref="paper",
                        yref="paper"))

# We need margins so the titles fit
fig.update_layout(margin=dict(t=80, r=20, l=120, b=50))
fig['data'][0]['showscale'] = True
fig.show()

# Let's also calculate some values that will be used throughout this exercise
# We already have actual values and corresponding predictions, defined above
correct = actual == predictions
tp = numpy.sum(correct & actual)
tn = numpy.sum(correct & numpy.logical_not(actual))
fp = numpy.sum(numpy.logical_not(correct) & actual)
fn = numpy.sum(numpy.logical_not(correct) & numpy.logical_not(actual))

print("TP - True Positives: ", tp)
print("TN - True Negatives: ", tn)
print("FP - False positives: ", fp)
print("FN - False negatives: ", fn)
TP - True Positives:  75
TN - True Negatives:  523
FP - False positives:  29
FN - False negatives:  33

Рассчитать метрики

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

  • Точность
  • Чувствительность/Отзыв
  • Специфика
  • Точность
  • Ложноположительный показатель

Давайте сначала вспомним некоторые полезные термины:
- TP = Истинные положительные результаты: правильно предсказана положительная метка
- TN = Истинно отрицательные значения: отрицательная метка прогнозируется правильно
- FP = Ложноположительные результаты: отрицательная метка прогнозируется как положительная< br /> - FN = ложноотрицательные результаты: положительная метка прогнозируется как отрицательная

Точность

Точность – это количество правильных прогнозов, разделенное на общее количество прогнозов. Возможно, это самая базовая используемая метрика, но, как мы видели, она не самая надежная при использовании несбалансированных наборов данных.

accuracy = (TP+TN) / number of samples
# Calculate accuracy
# len(actual) is the number of samples in the set that generated TP and TN
accuracy = (tp+tn) / len(actual) 

# print result as a percentage
print(f"Model accuracy is {accuracy:.2f}%")
Model accuracy is 0.91%

Чувствительность/Отзыв

Чувствительность и отзыв — это взаимозаменяемые названия одной и той же метрики, которая выражает долю выборок, правильно предсказанную моделью. Это важный показатель, который говорит нам, сколько из всех действительно положительных образцов правильно прогнозируются как положительные.

sensitivity = recall = TP / (TP + FN)
# code for sensitivity/recall
sensitivity = recall = tp / (tp + fn)

# print result as a percentage
print(f"Model sensitivity/recall is {sensitivity:.2f}%")
Model sensitivity/recall is 0.69%

Специфика

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

specificity = TN / (TN + FP)
# Code for specificity
specificity = tn / (tn + fp)

# print result as a percentage
print(f"Model specificity is {specificity:.2f}%")
Model specificity is 0.95%

Точность

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

precision = TP / (TP + FP)
# Code for precision

precision = tp / (tp + fp)

# print result as a percentage
print(f"Model precision is {precision:.2f}%")
Model precision is 0.72%

Ложноположительный показатель

Уровень ложноположительных результатов или FPR — это количество неверных положительных прогнозов, разделенное на общее количество отрицательных образцов. Это говорит нам о том, что из всех реальных негативов сколько было ошибочно классифицировано как позитивные?

false_positive_rate = FP / (FP + TN)
# Code for false positive rate
false_positive_rate = fp / (fp + tn)

# print result as a percentage
print(f"Model false positive rate is {false_positive_rate:.2f}%")
Model false positive rate is 0.05%

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

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

Краткое содержание

В этом упражнении мы говорили о следующих понятиях:

  • Как рассчитать самые основные измерения, используемые при оценке классификационных моделей: TP, FP, TN, FN.
  • Как использовать приведенное выше измерение для расчета более значимых показателей, таких как точность, чувствительность/память, специфичность, точность, уровень ложноположительных результатов.
  • Как выбор метрик зависит от набора данных и проблемы, которую мы пытаемся решить.

Приятного обучения!