使用特征脸和支持向量机进行人脸识别

Beginner

This tutorial is from open-source community. Access the source code

简介

本实验将指导你完成使用特征脸和支持向量机(SVM)进行人脸识别的步骤。本实验中使用的数据集是“Labeled Faces in the Wild”数据集的预处理摘录。

虚拟机提示

虚拟机启动完成后,点击左上角切换到“笔记本”标签页,以访问 Jupyter Notebook 进行练习。

有时,你可能需要等待几秒钟让 Jupyter Notebook 完成加载。由于 Jupyter Notebook 的限制,操作验证无法自动化。

如果你在学习过程中遇到问题,请随时向 Labby 提问。课程结束后提供反馈,我们将立即为你解决问题。

导入库

from time import time
import matplotlib.pyplot as plt

from sklearn.model_selection import train_test_split
from sklearn.model_selection import RandomizedSearchCV
from sklearn.datasets import fetch_lfw_people
from sklearn.metrics import classification_report
from sklearn.metrics import ConfusionMatrixDisplay
from sklearn.preprocessing import StandardScaler
from sklearn.decomposition import PCA
from sklearn.svm import SVC
from scipy.stats import loguniform

首先,我们需要导入所有必要的库。

加载并探索数据集

lfw_people = fetch_lfw_people(min_faces_per_person=70, resize=0.4)
n_samples, h, w = lfw_people.images.shape
X = lfw_people.data
n_features = X.shape[1]
y = lfw_people.target
target_names = lfw_people.target_names
n_classes = target_names.shape[0]

我们使用 scikit-learn 中的fetch_lfw_people()函数下载数据集。然后,我们通过获取图像的样本数量、高度和宽度来探索数据集。我们还获取输入数据X、目标y、目标名称target_names和类别数量n_classes

数据预处理

X_train, X_test, y_train, y_test = train_test_split(
    X, y, test_size=0.25, random_state=42
)
scaler = StandardScaler()
X_train = scaler.fit_transform(X_train)
X_test = scaler.transform(X_test)

我们将数据集拆分为训练集和测试集,并使用StandardScaler()函数对输入数据进行缩放,以此来预处理数据。

执行主成分分析(PCA)

n_components = 150

pca = PCA(n_components=n_components, svd_solver="randomized", whiten=True).fit(X_train)
eigenfaces = pca.components_.reshape((n_components, h, w))

X_train_pca = pca.transform(X_train)
X_test_pca = pca.transform(X_test)

我们执行主成分分析(PCA)以从输入数据中提取特征。我们将成分数量设置为 150,并将 PCA 模型拟合到训练数据上。然后,我们得到特征脸,并将输入数据转换为主成分。

训练支持向量机(SVM)分类模型

param_grid = {
    "C": loguniform(1e3, 1e5),
    "gamma": loguniform(1e-4, 1e-1),
}

clf = RandomizedSearchCV(
    SVC(kernel="rbf", class_weight="balanced"), param_grid, n_iter=10
)
clf = clf.fit(X_train_pca, y_train)

我们使用变换后的数据训练一个 SVM 分类模型。我们使用RandomizedSearchCV()来为 SVM 模型找到最佳超参数。

评估模型性能

y_pred = clf.predict(X_test_pca)
print(classification_report(y_test, y_pred, target_names=target_names))
ConfusionMatrixDisplay.from_estimator(
    clf, X_test_pca, y_test, display_labels=target_names, xticks_rotation="vertical"
)

我们使用测试数据预测目标值,并使用classification_report()函数评估模型性能。我们还使用ConfusionMatrixDisplay()函数绘制混淆矩阵。

可视化预测结果

def plot_gallery(images, titles, h, w, n_row=3, n_col=4):
    """辅助函数,用于绘制一组人像图片"""
    plt.figure(figsize=(1.8 * n_col, 2.4 * n_row))
    plt.subplots_adjust(bottom=0, left=0.01, right=0.99, top=0.90, hspace=0.35)
    for i in range(n_row * n_col):
        plt.subplot(n_row, n_col, i + 1)
        plt.imshow(images[i].reshape((h, w)), cmap=plt.cm.gray)
        plt.title(titles[i], size=12)
        plt.xticks(())
        plt.yticks(())

prediction_titles = [
    title(y_pred, y_test, target_names, i) for i in range(y_pred.shape[0])
]

plot_gallery(X_test, prediction_titles, h, w)

我们通过绘制一组人像图片来可视化预测结果,图片上标注有预测名称和真实名称。

可视化特征脸

eigenface_titles = ["特征脸 %d" % i for i in range(eigenfaces.shape[0])]
plot_gallery(eigenfaces, eigenface_titles, h, w)

plt.show()

我们还绘制特征脸,以可视化从输入数据中提取的特征。

总结

在本实验中,我们学习了如何使用特征脸和支持向量机来进行人脸识别。我们首先加载并探索了数据集,然后通过缩放输入数据对数据进行预处理。接着,我们执行主成分分析(PCA)从输入数据中提取特征,并训练了一个支持向量机分类模型。我们评估了模型性能,并可视化了预测结果和特征脸。