分類算法評價
在之前分類中我們常用MSE MAE等 算法來做分類評價。舉個例子,極度偏斜的情況。在1000個人中,有1個是生病的。假設(shè)生病為1,沒生病為0。那么我們只需要預(yù)測所有人都沒有生病,那么我們的評估算法會給我們的算法評價為99.99%正確率。這樣在現(xiàn)實生活中一定會出現(xiàn)問題。如何解決呢?

上圖為混淆矩陣,我們可以換一個角度進行評價,原本是判斷預(yù)測結(jié)果和真實結(jié)果是否相同,現(xiàn)在我們這里分成了4個角度,分別如下。假設(shè)我們做了10000次預(yù)測,預(yù)測結(jié)果有兩種,一種為有病1,一種為沒病0。
- TN:我們預(yù)測無病,真實無病的人數(shù)
- FN:我們預(yù)測無病,真實有病的人數(shù)
- FP:我們預(yù)測有病,真實無病的人數(shù)
- TP:我們預(yù)測有病,真實有病的人數(shù)
精準率 precision
預(yù)測正確有病的人在所有預(yù)測到有病的人中的概率。換句話說,預(yù)測到這么多人中有多少是預(yù)測準確的。
召回率 recall
預(yù)測正確有病的人在所有有病的人中的概率。換句話說,真實這么多人中,有多少被預(yù)測準確了。
scikit-learn
from sklearn.metrics import confusion_matrix
# 獲得混淆矩陣
confusion_matrix(y_test, y_log_predict)
from sklearn.metrics import precision_score
# 計算精準度
precision_score(y_test, y_log_predict)
from sklearn.metrics import recall_score
# 計算召回率
recall_score(y_test, y_log_predict)
精準率和召回率哪個重要呢?
根據(jù)具體情況而定,例如股票預(yù)測中,當我們預(yù)測股票為漲,結(jié)果卻跌了,那么就是精準率不高,容易虧錢。所以這個情況應(yīng)該是要精準率高一些。而在醫(yī)療診斷系統(tǒng)中。如果一個病人被診斷為沒病,那么病人病情就會惡化下去,后果會非常嚴重,所以召回率比較重要。
F1 Score
兼顧了精準率和召回率,是精準率和召回率的調(diào)和平均值。
調(diào)和平均值算法,優(yōu)勢,當兩者同時高時,最終得分才會高。否則僅僅一端高時結(jié)果也是低的

變形

from sklearn.metrics import f1_score
f1_score(y_test, y_predict)
精準率和召回率曲線
閾值
在邏輯回歸中,當結(jié)果分為是和否的時候。我們把計算出來的值如果大于0則為是,小于0則為否。0這個值就是閾值,當我們調(diào)整閾值時,就會造成不同的精準率和召回率,閾值越高,精準率越高,召回率越低。閾值越低則相反。

精準率:藍色曲線
召回率:黃色曲線
X:閾值
Y:精準率和召回率各自的值
精準率-召回率 曲線

X:精準率
Y:召回率
scikit-learn
from sklearn.metrics import precision_recall_curve
#precisions精準率,recalls召回率,thresholds閾值向量
precisions, recalls, thresholds = precision_recall_curve(y_test, decision_scores)#y_test真實標簽,decision_scores分類的評分
plt.plot(thresholds, precisions[:-1])#精準率曲線,[:-1]因為thresholds比precisions個數(shù)少1
plt.plot(thresholds, recalls[:-1])#召回率曲線
plt.show()
plt.plot(precisions, recalls)#精準率-召回率曲線
plt.show()
ROC曲線

-
FPR
所有真實值為0,預(yù)測為1的概率
-
TPR
所有真實值為1中,預(yù)測為1的概率

如上圖,不難看出當閾值越低時,TPR和FPR同時在增大,否則反之

X:FPR
Y:TPR

當FPR越小時,TPR越高則說明分類算法越好。所以衡量一個模型分類的效果就是看這條曲線包住的塊的面積的大小, 越大則效果越好
scikit-learn
from sklearn.metrics import roc_curve
fprs, tprs, thresholds = roc_curve(y_test, decision_scores)
plt.plot(fprs, tprs)
plt.show()
from sklearn.metrics import roc_auc_score
roc_auc_score(y_test, decision_scores)#求面積
多分類問題中的混淆矩陣
手寫數(shù)字為例
import numpy as np
import matplotlib.pyplot as plt
from sklearn.linear_model import LogisticRegression
from sklearn import datasets
from sklearn.metrics import precision_score
digits = datasets.load_digits()
X = digits.data
y = digits.target
from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.8, random_state=666)
log_reg = LogisticRegression()
log_reg.fit(X_train, y_train)
log_reg.score(X_test, y_test)
y_predict = log_reg.predict(X_test)
# 計算精準率
precision_score(y_test, y_predict, average="micro")# average="micro"選擇多分類的算法來計算精準率
from sklearn.metrics import confusion_matrix
# 混淆矩陣
cfm = confusion_matrix(y_test, y_predict)
# 看正確的分類混淆矩陣圖
plt.matshow(cfm, cmap=plt.cm.gray)# 使用灰度圖來展示混淆矩陣,越白為越正確
plt.show()
# 看錯誤的分類混淆矩陣圖(我們主要目的是分析錯誤的情況,看錯誤的比較常用)
row_sums = np.sum(cfm, axis=1)# 將混淆舉證按列相加(求得各分類總樣本數(shù))
err_matrix = cfm / row_sums # 獲取個元素的比重
np.fill_diagonal(err_matrix, 0)# 將對角線設(shè)為0,對角線為預(yù)測和實際相同的情況
plt.matshow(err_matrix, cmap=plt.cm.gray)# 按照比重繪制,比重越大越白
plt.show()