PCA+SVM实现基础的人脸识别

PCA+SVM实现基础的人脸识别
人工智能课程作业,顺便上传一下

PCA+SVM实现基础的人脸识别

本实验采用python编程实现,使用Olivette实验室的ORL人脸库作为数据集。ORL人脸库共有400幅人脸图像 (40人, 每人10幅, 大小为112像素×92像素) , 大多数图像的光照方向和强度相差不大, 其中人的脸部表情和脸部细节有着不同程度的变化, 尺度差异在10%左右, 人脸姿态也有相当程度的变化。将数据集中每个人的10张人脸图像分成两组前7张构成训练集, 另外3张构成测试集。训练集和测试集各有280个和120个人脸图像样本。
实验过程:
利用PCA降维去除像素之间的相关性,从训练集样本中提取主要成分,实验中将主成分的 数目确定为20。通过这样的处理,训练集中的每个人脸样本的特征向量由10304维降到20维,在后续的实验中就以20维的特征向量来代表该人脸样本。在后续的实验中就以20维的特征向量来代表该人脸样本
采用最为常用径向基核函数 (RBF) , 得到的支持向量机是一种径向基核函数分类器。在实验中采用python中SVM的默认值(C=1.0, kernel=“rbf”, degree=3, gamma=“scale”……),对测试集中的40个人的三张随机照片,共120张照片进行分类,显示实别正确率是95.8%

代码

调用的库主要是Image 和sklearn
有一些是测试的时候随手复制的 没删

from PIL import Image;
import numpy as np;
import os;
import time
from sklearn.neural_network import MLPClassifier
from sklearn.model_selection import train_test_split
from sklearn.decomposition import PCA
from sklearn.model_selection import  StratifiedKFold,KFold
from sklearn.model_selection import GridSearchCV
from sklearn.svm import SVC
import matplotlib.pyplot as plt
import random
from sklearn import svm

读取图片,变为灰度形式,并以一维的形式存储每一张图片

rootdir = 'D:\网页\人工智能\orl_faces'
list1 = os.listdir(rootdir) #列出文件夹下所有的目录与文件
list_title = list()
list_pho =list()
for i in range(0,40):
        #第一层 data下的目录
        path1 = os.path.join(rootdir,list1[i])
        list2 = os.listdir(path1)
        for k in range(0,len(list2)):
            #第2层 1下的目录
            path2 = os.path.join(path1,list2[k])
            raw_image=Image.open(path2).convert('L')
            list_pho.append( list(raw_image.getdata()) )
            list_title.append(i+1)

简单的PCA降维
每个人脸样本的特征向量由10304维降到20维

n_components = 20#这个降维后的特征值个数如果太大,比如100,结果将极其不准确,为何??
pca = PCA(n_components = n_components, svd_solver='auto',
          whiten=True).fit(list_pho)
#PCA降维后的总数据集
list_pho_pca = pca.transform(list_pho)

将数据随机分成训练集和测试集

X_train = list()
y_train = list()
X_test = list()
y_test = list()
a = [0,1,2,3,4,5,6,7,8,9]
for i in range(0,400,10):
    random.shuffle(a)
    for k in range(0,7):
        X_train.append(list_pho_pca[i+a[k]])
        y_train.append(list_title[i+a[k]])
    for k in range(7,10):
        X_test.append(list_pho_pca[i+a[k]])
        y_test.append(list_title[i+a[k]])  

使用SVM分类器,全部为默认参数

model = svm.SVC(C=1) 

model.fit(X_train, y_train)

print(model.score(X_test, y_test))

实验结果分析

  1. PCA可有效降维, 如实验中人脸图像样本的特征向量10304维降为20维, 这就将后续的分类问题变成一个在20维空间中的划分问题, 过程大大简化, 提高了运算速度。

  2. 降维以后, 分类的识别率没有明显下降。这是因为经过PCA处理后, 虽然特征向量的维数大大降低, 但是图像中那些差异最大的特征被最大程度的保留, 而那些相对一致、区分力较差的特征则被丢弃。PCA降维丢弃某些特征所损失的信息, 可以通过在低维空间中更加精确地映射得以补偿。

  3. SVM选取不同参数进行分类, 得到了不同的识别结果, 说明参数的优化可提高识别率, 可以起到提高SVM分类器推广能力的作用。

完整代码

from PIL import Image;
import numpy as np;
import os;
import time
from sklearn.neural_network import MLPClassifier
from sklearn.model_selection import train_test_split
from sklearn.decomposition import PCA
from sklearn.model_selection import  StratifiedKFold,KFold
from sklearn.model_selection import GridSearchCV
from sklearn.svm import SVC
import matplotlib.pyplot as plt
import random
from sklearn import svm

rootdir = 'D:\网页\人工智能\orl_faces'
list1 = os.listdir(rootdir) #列出文件夹下所有的目录与文件
list_title = list()
list_pho =list()
for i in range(0,40):
        #第一层 data下的目录
        path1 = os.path.join(rootdir,list1[i])
        list2 = os.listdir(path1)
        for k in range(0,len(list2)):
            #第2层 1下的目录
            path2 = os.path.join(path1,list2[k])
            raw_image=Image.open(path2).convert('L')
            list_pho.append( list(raw_image.getdata()) )
            list_title.append(i+1)
            
    
n_components = 20#这个降维后的特征值个数如果太大,比如100,结果将极其不准确,为何??
pca = PCA(n_components = n_components, svd_solver='auto',
          whiten=True).fit(list_pho)
#PCA降维后的总数据集
list_pho_pca = pca.transform(list_pho)

X_train = list()
y_train = list()
X_test = list()
y_test = list()
a = [0,1,2,3,4,5,6,7,8,9]
for i in range(0,400,10):
    random.shuffle(a)
    for k in range(0,7):
        X_train.append(list_pho_pca[i+a[k]])
        y_train.append(list_title[i+a[k]])
    for k in range(7,10):
        X_test.append(list_pho_pca[i+a[k]])
        y_test.append(list_title[i+a[k]])    

print(len(X_train))
print(len(X_test))
#Assumed you have, X (predictor) and Y (target) for training data set and x_test(predictor) of test_dataset
# Create SVM classification object 
model = svm.SVC(C=1) 
# there is various option associated with it, like changing kernel, gamma and C value. Will discuss more # about it in next section.Train the model using the training sets and check score
model.fit(X_train, y_train)

print(model.score(X_test, y_test))

生活中用python比较少,主要是课程需要,所以代码写的可能有些奇怪,望海涵

关于数据集

使用Olivette实验室的ORL人脸库
可以直接github上搜索 orl 找到orl_faces 之类的直接下载就好了

第二次修改

分享了数据集

链接:https://pan.baidu.com/s/1gIpA-tsyw51fUbRqYMUBKg?pwd=fzpk 提取码:fzpk

你可能感兴趣的:(人工智能,支持向量机,机器学习,python,pca降维)