返回文章列表

深度學習模型解釋性與SHAP應用

本文探討深度學習模型解釋性,以卷積神經網路(CNN)為例,講解如何使用 SHAP(SHapley Additive exPlanations)解釋模型預測。文章涵蓋 MNIST、CIFAR-10 資料集上的 DeepExplainer 應用、SHAP 值視覺化、模型評估以及反事實解釋等內容,並提供程式碼範例。

深度學習 機器學習

深度學習模型的內部機制複雜,難以理解其預測原因。SHAP 值提供了一種有效的方法來解釋模型預測,幫助我們理解每個特徵對預測結果的貢獻。本文以影像分類別和表格資料為例,演示如何使用 SHAP 解釋深度學習模型,並特別介紹了反事實解釋的應用和 Alibi 函式庫的使用。透過 SHAP 值的視覺化,可以直觀地理解模型的決策過程,進而提升模型的可信度和透明度。針對影像資料,我們使用 MNIST 和 CIFAR-10 資料集訓練 CNN 模型,並使用 DeepExplainer 計算 SHAP 值,將其視覺化,以便觀察每個畫素對預測的影響。對於表格資料,我們以葡萄酒品質預測為例,展示瞭如何使用 DeepExplainer 解釋模型預測,並分析特徵重要性。最後,我們介紹了反事實解釋的概念和應用,以及如何使用 Alibi 函式庫生成反事實解釋,以理解模型在哪些情況下會做出不同的預測。

深度學習模型的解釋性:以卷積神經網路為例

深度學習模型在影像分類別任務中表現出色,但其內部運作機制往往難以理解。本章節將介紹如何使用SHAP(SHapley Additive exPlanations)來解釋深度學習模型的預測結果。

MNIST資料集上的DeepExplainer

首先,我們使用MNIST資料集訓練了一個卷積神經網路(CNN)模型,並使用DeepExplainer來解釋模型的預測結果。DeepExplainer是一種根據SHAP的解釋方法,適用於深度學習模型。

# 載入MNIST資料集
from keras.datasets import mnist
(x_train, y_train), (x_test, y_test) = mnist.load_data()

# 建立DeepExplainer物件
explainer = shap.DeepExplainer(model, x_train)

# 取得SHAP值
shap_values = explainer.shap_values(x_test[5:9])

內容解密:

  • shap.DeepExplainer用於建立一個DeepExplainer物件,該物件用於解釋深度學習模型的預測結果。
  • explainer.shap_values方法用於取得輸入資料的SHAP值,SHAP值表示每個特徵對模型預測結果的貢獻程度。

CIFAR-10資料集上的DeepExplainer

接下來,我們使用CIFAR-10資料集訓練了一個CNN模型,並使用DeepExplainer來解釋模型的預測結果。CIFAR-10資料集包含60,000張32x32的彩色影像,共10個類別。

# 載入CIFAR-10資料集
from keras.datasets import cifar10
(X_train, y_train), (X_test, y_test) = cifar10.load_data()

# 建立CNN模型
model = Sequential()
model.add(Conv2D(32, (3, 3), padding='same', input_shape=(32, 32, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
model.add(Dropout(0.25))
model.add(Flatten())
model.add(Dense(512))
model.add(Activation('relu'))
model.add(Dropout(0.5))
model.add(Dense(10))
model.add(Activation('softmax'))

# 編譯模型
model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

# 訓練模型
history = model.fit(X_train, Y_train, batch_size=128, epochs=20, validation_split=0.2)

內容解密:

  • Conv2D層用於提取影像特徵。
  • MaxPooling2D層用於降維和減少引數數量。
  • Dropout層用於防止過擬合。
  • Flatten層用於將多維資料展平為一維資料。
  • Dense層用於進行分類別。

SHAP值的視覺化

使用SHAP值,我們可以視覺化模型的預測結果。以下是一個例子:

# 取得SHAP值
shap_values = explainer.shap_values(X_test[10:15])

# 繪製SHAP值
shap.image_plot(shap_values, -X_test[10:15])

內容解密:

  • shap.image_plot函式用於繪製SHAP值,顯示每個特徵對模型預測結果的貢獻程度。

模型評估

模型的準確度和損失函式可以用於評估模型的效能。

# 評估模型
score = model.evaluate(X_test, Y_test, batch_size=128)

# 繪製準確度和損失函式
plt.plot(history.history['accuracy'])
plt.plot(history.history['val_accuracy'])
plt.title('Model Accuracy')
plt.xlabel('Epoch')
plt.ylabel('Accuracy')
plt.legend(['Train', 'Test'], loc='upper left')
plt.show()

內容解密:

  • model.evaluate方法用於評估模型的效能。
  • history.history屬性包含模型的訓練歷史記錄,包括準確度和損失函式。

深度學習模型的解釋性:以影像和表格資料為例

深度學習模型在影像分類別和表格資料分析等領域取得了顯著的成就。然而,這些模型的複雜性使得理解其預測結果變得困難。本章將介紹如何使用SHAP(SHapley Additive exPlanations)函式庫中的DeepExplainer來解釋深度學習模型的預測結果。

影像資料的解釋:以MNIST和CIFAR資料集為例

首先,我們使用MNIST手寫數字資料集和CIFAR影像資料集來展示如何使用SHAP來解釋深度學習模型的預測結果。

import shap
shap.image_plot(shap_values, -X_test[10:15])

內容解密:

這段程式碼用於繪製影像資料的SHAP值。shap_values代表了每個畫素對模型預測結果的貢獻,而-X_test[10:15]則是選擇了測試資料集中的第10到15張影像進行分析。負號表示對影像進行了反色處理,以便更好地展示SHAP值。

import pandas as pd
pd.DataFrame(model.predict_classes(X_test)).head(10)

內容解密:

這段程式碼用於輸出模型對測試資料集前10筆資料的預測類別。model.predict_classes(X_test)得到了模型的預測結果,而pd.DataFrame().head(10)則將結果轉換為DataFrame並顯示前10行。

表格資料的解釋:以葡萄酒品質預測為例

接下來,我們使用一個複雜的表格資料集——葡萄酒品質預測資料集,來展示如何使用DeepExplainer解釋深度學習模型的預測結果。

from keras.models import Sequential
from sklearn.metrics import accuracy_score
from sklearn.preprocessing import StandardScaler
import pandas as pd
import numpy as np

feature_names = [
    "fixed acidity",
    "volatile acidity",
    "citric acid",
    "residual sugar",
    "chlorides",
    "free sulfur dioxide",
    "total sulfur dioxide",
    "density",
    "pH",
    "sulphates",
    "alcohol",
    "quality",
]

red_wine_data = pd.read_csv('https://archive.ics.uci.edu/ml/machine-learning-databases/wine-quality/winequality-red.csv', names=feature_names, sep=";", header=1)
white_wine_data = pd.read_csv('https://archive.ics.uci.edu/ml/machine-learning-databases/wine-quality/winequality-white.csv', names=feature_names, sep=";", header=1)

wine_data = red_wine_data.append(white_wine_data)
wine_features = wine_data[feature_names].drop('quality', axis=1).values
wine_quality = wine_data['quality'].values

scaler = StandardScaler().fit(wine_features)
wine_features = scaler.transform(wine_features)

內容解密:

這段程式碼首先定義了葡萄酒品質資料集的特徵名稱。然後,從UCI機器學習倉函式庫中讀取紅葡萄酒和白葡萄酒的資料,並將它們合併。接著,對特徵進行了標準化處理,以便於深度學習模型的訓練。

model = Sequential()
model.add(Dense(1024, input_dim=11, activation='tanh'))
model.add(Dense(512, activation='tanh'))
model.add(Dense(64, activation='tanh'))
model.add(Dense(1))
model.compile(loss='mse', optimizer='adam', metrics=['accuracy'])
model.summary()

history = model.fit(wine_features, wine_quality,
                    batch_size=BATCH_SIZE,
                    epochs=NB_EPOCH,
                    validation_split=VALIDATION_SPLIT,
                    verbose=VERBOSE)

background = wine_features[np.random.choice(wine_features.shape[0],100, replace=False)]
explainer = shap.DeepExplainer(model, background)
shap_values = explainer.shap_values(wine_features)

內容解密:

這段程式碼構建了一個三層的深度神經網路模型,並對其進行了訓練。訓練完成後,使用SHAP的DeepExplainer來解釋模型的預測結果。background是從訓練資料中隨機選取的100筆資料,用於計算SHAP值。shap_values代表了每個特徵對模型預測結果的貢獻。

反事實解釋在XAI模型中的應用

反事實解釋(Counterfactual Explanations, CFEs)是一種用於解釋機器學習模型預測結果的方法,特別是在人工智慧(AI)和可解釋性AI(XAI)領域。反事實解釋透過建立假設性場景並在這些場景下生成預測結果,從而提供對模型預測的深入理解。

反事實解釋的基本概念

反事實解釋是一種因果關係的體現,用於描述機器學習模型預測過程中的因果鏈。它們提供了一種區域性解釋,即針對個別預測結果生成相關的解釋。反事實解釋對於非技術使用者和業務人員來說是容易理解的,因為它們創造了假設性場景並在這些場景下進行預測。

使用Alibi實作反事實解釋

Alibi是一個Python函式庫,用於生成反事實解釋。它支援Python 3.6及以上版本。要安裝Alibi,可以使用以下命令:

!pip install alibi
!pip install alibi[ray]

安裝完成後,可以透過以下程式碼檢查Alibi的版本:

import alibi
print(alibi.__version__)

內容解密:

  1. !pip install alibi:安裝Alibi函式庫。
  2. !pip install alibi[ray]:安裝Alibi的額外依賴,包括Ray。
  3. import alibi:匯入Alibi函式庫。
  4. print(alibi.__version__):輸出Alibi的版本號,以驗證安裝是否成功。

使用Alibi生成反事實解釋的步驟

  1. 訓練模型:首先,需要訓練一個機器學習模型。以下範例使用極端梯度提升(XGBoost)分類別器對糖尿病資料集進行訓練。

    import pandas as pd
    import xgboost as xgb
    from sklearn.model_selection import train_test_split
    from sklearn.metrics import accuracy_score, confusion_matrix
    
    # 載入資料
    data = pd.read_csv('diabetes.csv')
    
    # 分割資料為訓練集和測試集
    y = data['Outcome']
    x = data[['Pregnancies', 'Glucose', 'BloodPressure', 'SkinThickness', 'Insulin', 'BMI', 'DiabetesPedigreeFunction', 'Age']]
    x_train, x_test, y_train, y_test = train_test_split(x, y, random_state=1234)
    
    # 訓練XGBoost模型
    bst = xgb.XGBClassifier(objective='reg:logistic')
    bst.fit(x_train, y_train)
    
    # 進行預測並評估模型
    y_pred = bst.predict(x_test)
    acc = accuracy_score(np.array(y_test), y_pred)
    print(acc)
    
    # 列印混淆矩陣
    cm = confusion_matrix(y_test, y_pred)
    print(cm)
    

    內容解密:

    1. 載入必要的函式庫,包括pandasxgboostsklearn的相關模組。
    2. 使用pd.read_csv載入糖尿病資料集。
    3. 將資料分割為特徵(x)和目標變數(y),然後進一步分割為訓練集和測試集。
    4. 初始化一個XGBoost分類別器並使用訓練資料進行訓練。
    5. 使用測試資料進行預測,並計算模型的準確率和混淆矩陣。
  2. 儲存模型:訓練完成後,儲存模型以便後續使用。

    bst.save_model('model.bst')
    

    內容解密:

    1. bst.save_model('model.bst'):將訓練好的XGBoost模型儲存到檔案model.bst中。
  3. 使用Alibi生成反事實解釋:將儲存的模型載入Alibi,並使用它生成反事實解釋。

反事實解釋的應用

反事實解釋可以應用於迴歸和分類別任務。它們幫助理解模型的預測結果,並提供對模型行為的深入洞察。透過創造假設性場景,反事實解釋能夠展示如果輸入資料有所不同,模型的預測結果將如何變化。

反事實解釋在 XAI 模型中的應用

模型預測與特徵重要性分析

在糖尿病預測模型中,透過 XGBoost 模型進行訓練後,我們可以觀察到模型的預測結果與實際結果之間的對應關係。同時,藉由分析特徵重要性,我們發現血糖水平(Glucose)、BMI、年齡(Age)和胰島素水平(Insulin)是預測糖尿病的重要特徵。

程式碼範例:特徵重要性分析

result = pd.DataFrame()
result['features_importance'] = bst.feature_importances_
result['feature_names'] = x_train.columns
result.sort_values(by=['features_importance'], ascending=False)

內容解密:

  1. 特徵重要性計算bst.feature_importances_ 用於取得 XGBoost 模型中各特徵的重要性得分。
  2. 結果整理:將特徵重要性得分和對應的特徵名稱存入 DataFrame 中,並按重要性得分進行降序排序。
  3. 分析意義:此步驟幫助我們瞭解哪些特徵對模型的預測結果影響最大。

特徵值的微小變化對預測結果的影響

透過對訓練資料集中的特定記錄進行微小的特徵值變更,我們可以觀察到預測結果的變化。這種方法幫助我們理解模型對於不同輸入的敏感度。

程式碼範例:變更特徵值並觀察預測結果

x_train.iloc[3] = [1, 117, 60, 23, 106, 33.8, 0.466, 27]
x_train.head()
bst.predict(x_train.head())

內容解密:

  1. 變更特徵值:選擇訓練資料集中的某一行記錄,並對其特徵值進行微小的變更。
  2. 重新預測:使用變更後的特徵值進行模型的預測。
  3. 比較結果:比較變更前後的預測結果,以瞭解模型的穩定性和對輸入變化的敏感度。

使用 Alibi 進行反事實解釋

Alibi 提供了一個框架,用於生成反事實解釋,幫助我們理解模型在哪些情況下會做出不同的預測。透過調整輸入特徵值,我們可以找到導致預測結果變化的邊界情況。

程式碼範例:使用 Alibi 生成反事實解釋

cf = CounterFactualProto(predict_fn, shape, use_kdtree=False, theta=10., max_iterations=1000,
                         feature_range=(np.array(x_train).min(axis=0), np.array(x_train).max(axis=0)),
                         c_init=1., c_steps=10)
cf.fit(x_train)

內容解密:

  1. 初始化反事實直譯器:使用 CounterFactualProto 類別初始化反事實直譯器,並設定相關引數,如 predict_fn(模型的預測函式)、shape(輸入資料的形狀)等。
  2. 擬合訓練資料:使用訓練資料集對反事實直譯器進行擬合。
  3. 生成反事實解釋:透過反事實直譯器生成對於特定輸入的反事實解釋,幫助理解模型的決策邊界。