700字范文,内容丰富有趣,生活中的好帮手!
700字范文 > 机器学习——SVM(支持向量机)与人脸识别

机器学习——SVM(支持向量机)与人脸识别

时间:2019-01-13 05:48:32

相关推荐

机器学习——SVM(支持向量机)与人脸识别

目录

系列文章目录

一、SVM的概念与原理

1.SVM简介

2.SVM基本流程

3.SVM在多分类中的推广

二、经典SVM运用于图像识别分类

三、SVM运用于人脸识别

1.预处理

1.1数据导入与处理

1.2数据降维

2.人脸识别

2.1 OVO实现SVM

2.2 OVR实现SVM

3.PCA与LDA分别结合SVM在各维度、各数据集的人脸识别率及其与KNN的对比

3.1 ORL下比较SVM与KNN对于PCA和LDA的人脸识别率随维度的改变

3.2各种方法在不同数据集下的平均人脸识别率

4.OVO与OVR实现SVM的人脸识别率比较

4.1ORL下比较OVO与OVR实现SVM + PCA的人脸识别率随维度的改变

4.2OVO与OVR实现SVM + PCA在不同数据集下的平均人脸识别率

四、创新SVM算法设计

五、其他

1.数据集及资源

2. 参考资料

总结

系列文章目录

本系列博客重点在机器学习的概念原理与代码实践,不包含繁琐的数学推导(有问题欢迎在评论区讨论指出,或直接私信联系我)。

代码可以全抄大家搞懂原理与流程去复现才是有意义的!!!

第一章机器学习——PCA(主成分分析)与人脸识别_@李忆如的博客-CSDN博客

第二章机器学习——LDA (线性判别分析) 与人脸识别_@李忆如的博客-CSDN博客

第三章机器学习——LR(线性回归)、LRC(线性回归分类)与人脸识别_@李忆如的博客​​​​​

第四章 机器学习——SVM(支持向量机)与人脸识别

梗概

本篇博客主要介绍SVM(支持向量机)算法,利用经典SVM实现图像识别二分类,并将SVM(OVO与OVR均实现)+ 降维方法(PCA与LDA)用于人脸识别,并将SVM与KNN进行比较,OVO与OVR进行比较(内附数据集与matlab、python代码)

一、SVM的概念与原理

1.SVM简介

支持向量机(SVM)是在分类与回归中分析数据的有监督学习模型与相关的学习算法。本质上是一种二分类模型,它的经典模型是定义在特征空间的间隔最大的线性分类器,学习策略是间隔最大化

2.SVM基本流程

SVM模型将实例表示为空间(超平面、超空间)中的点,这样映射就使得单独类别的实例被尽可能宽的明显的间隔分开。然后,将新的实例映射到同一空间,并基于它们落在间隔的哪一侧来预测所属类别。

3.SVM在多分类中的推广

由于SVM是一种二分类器,即用一条线或一个平面分开两类不同数据,一般用如下两个方法使其推广到多分类。

① OVR:对于K个类别的情况,训练K个SVM,第j个SVM用于判断任意条数据是属于类别j还是类别非j。预测的时候,具有距超空间i最大值的表示给定的数据x属于类别i。

② OVO:对于K个类别的情况,训练K*(K-1)/2个SVM,每一个SVM只用于判断任意条数据是属于K中的特定两个类别。预测的时候,使用K*(K-1)/2个SVM做K*(K-1)/2次预测,使用计票的方式决定数据被分类为哪个类别的次数最多,就认为数据x属于此类别。

Tips:SVM详细推导可见:svm原理详细推导_weixin_42001089的博客-CSDN博客_svm推导

二、经典SVM运用于图像识别分类

① 问题描述:识别图片属于森林还是房间

② 算法实现核心:使用mapminmax实现划分后的数据集归一化,利用函数fitcsvm训练归一化后训练集,通过求解二次规划与准备参数,得到a并找到支持向量,predict用刚刚训练出的模型预测,求b得到f(x)与预测类别。

③ 代码如下:

clear;% dataset是将bedroom和forest合并;dataset = [bedroom;forset];这行代码可以实现合并load forest.mat %导入要分类的数据集load bedroom.matdataset = [bedroom;MITforest];load labelset.mat%导入分类集标签集% 选定训练集和测试集% 将第一类的1-5,第二类的11-15做为训练集train_set = [dataset(1:5,:);dataset(11:15,:)];% 相应的训练集的标签也要分离出来train_set_labels = [lableset(1:5);lableset(11:15)];% 将第一类的6-10,第二类的16-20,做为测试集test_set = [dataset(6:10,:);dataset(16:20,:)];% 相应的测试集的标签也要分离出来test_set_labels = [lableset(6:10);lableset(16:20)];% 数据预处理,将训练集和测试集归一化到[0,1]区间[mtrain,ntrain] = size(train_set);[mtest,ntest] = size(test_set);test_dataset = [train_set;test_set];% mapminmax为MATLAB自带的归一化函数[dataset_scale,ps] = mapminmax(test_dataset',0,1);dataset_scale = dataset_scale';train_set = dataset_scale(1:mtrain,:);test_set = dataset_scale( (mtrain+1):(mtrain+mtest),: );% SVM网络训练model = fitcsvm(train_set,train_set_labels);% SVM网络预测[predict_label] = predict(model,test_set);%[predict_label] = model.IsSupportVector;% 结果分析% 测试集的实际分类和预测分类图% 通过图可以看出只有一个测试样本是被错分的figure;hold on;plot(test_set_labels,'o');plot(predict_label,'r*');xlabel('测试集样本','FontSize',12);ylabel('类别标签','FontSize',12);legend('实际测试集分类','预测测试集分类');title('测试集的实际分类和预测分类图','FontSize',12);grid on;

④ 识别效果如下:

分析:分析上图可知,预测分类与实际分类均相等,预测效果很好。

三、SVM运用于人脸识别

1.预处理

1.1数据导入与处理

利用imread批量导入人脸数据库,或直接load相应mat文件,并在导入时不断将人脸拉成一个个列向量组成reshaped_faces,并取出n%作为测试数据,剩下100-n%作为训练数据,重复此步骤,将导入数据抽象成框架,可以匹配不同数据集的导入(本实验框架适配ORL、AR、FERET数据集)。

Tips:代码可见本系列第二篇文章(LDA与人脸识别),基本一致。

1.2数据降维

使用LDA或PCA对数据降维(具体原理与详细代码见本系列一二篇文章)

% LDA% 算每个类的平均k = 1; class_mean = zeros(dimension, people_num); for i=1:people_num% 求一列(即一个人)的均值temp = class_mean(:,i);% 遍历每个人的train_pic_num_of_each张用于训练的脸,相加算平均for j=1:train_pic_num_of_eachtemp = temp + train_data(:,k);k = k + 1;endclass_mean(:,i) = temp / train_pic_num_of_each;end% 算类类间散度矩阵SbSb = zeros(dimension, dimension);all_mean = mean(train_data, 2); % 全部的平均for i=1:people_num% 以每个人的平均脸进行计算,这里减去所有平均,中心化centered_data = class_mean(:,i) - all_mean;Sb = Sb + centered_data * centered_data';endSb = Sb / people_num;% 算类内散度矩阵SwSw = zeros(dimension, dimension);k = 1; % p表示每一张图片for i=1:people_num % 遍历每一个人for j=1:train_pic_num_of_each % 遍历一个人的所有脸计算后相加centered_data = train_data(:,k) - class_mean(:,i);Sw = Sw + centered_data * centered_data';k = k + 1;endendSw = Sw / (people_num * train_pic_num_of_each);% 目标函数一:经典LDA(伪逆矩阵代替逆矩阵防止奇异值)% target = pinv(Sw) * Sb;% PCAcentered_face = (train_data - all_mean);cov_matrix = centered_face * centered_face';target = cov_matrix;% 求特征值、特征向量[eigen_vectors, dianogol_matrix] = eig(target);eigen_values = diag(dianogol_matrix);% 对特征值、特征向量进行排序[sorted_eigen_values, index] = sort(eigen_values, 'descend'); eigen_vectors = eigen_vectors(:, index);eigen_vectors = real(eigen_vectors); % 处理复数,会导致一定误差(LDA用)

2.人脸识别

实现核心流程:使用PCA/LDA先对数据进行预处理与降维,SVM使用OVO/OVR对划分好的数据集进行模型训练与测试集预测,最终记录识别率并与比较。

2.1 OVO实现SVM

%使用SVM人脸识别% SVM(OVO)rate = []; %用于记录人脸识别率for i=10:10:160right_num = 0;% 降维得到投影矩阵project_matrix = eigen_vectors(:,1:i);projected_train_data = project_matrix' * (train_data - all_mean);projected_test_data = project_matrix' * (test_data - all_mean);% SVM训练过程model_num = 1;for j = 0:1:people_num - 2train_img1 = projected_train_data(:,j * train_pic_num_of_each + 1 : j * train_pic_num_of_each + train_pic_num_of_each); % 取出每次SVM需要的训练集train_label1 = ones(1,train_pic_num_of_each)*(j + 1); % 给定训练标签test_img1 = projected_test_data(:,j * test_pic_num_of_each + 1 : j * test_pic_num_of_each + test_pic_num_of_each); % 取出每次SVM需要的测试集for z = j + 1:1:people_num - 1train_img2 = projected_train_data(:,z * train_pic_num_of_each + 1 : z * train_pic_num_of_each + train_pic_num_of_each); % 取出每次SVM需要的训练集train_label2 = ones(1,train_pic_num_of_each)*(z + 1); % 给定训练标签train_imgs = [train_img1,train_img2];train_label = [train_label1,train_label2];test_img2 = projected_test_data(:,z * test_pic_num_of_each + 1 : z * test_pic_num_of_each + test_pic_num_of_each); % 取出每次SVM需要的测试集test_imgs = [test_img1,test_img2];% 数据预处理,将训练集和测试集归一化到[0,1]区间 [mtrain,ntrain] = size(train_imgs); %m为行数,n为列数[mtest,ntest] = size(test_imgs);test_dataset = [train_imgs,test_imgs];% mapminmax为MATLAB自带的归一化函数[dataset_scale,ps] = mapminmax(test_dataset,0,1);train_imgs = dataset_scale(:,1:ntrain);test_imgs = dataset_scale( :,(ntrain+1):(ntrain+ntest) );% SVM网络训练train_imgs = train_imgs';train_label = train_label';expr = ['model_' num2str(model_num) ' = fitcsvm(train_imgs,train_label);']; % fitcsvm默认读取数据为按行,一张一脸为一列,需要转置eval(expr);model_num = model_num + 1;endendmodel_num = model_num - 1;% 人脸识别test = []; % 测试用for k = 1:1:test_pic_num_of_each * people_numtest_img = projected_test_data(:,k); % 取出待识别图像test_real_label = fix((k - 1) / test_pic_num_of_each) + 1; % 给定待测试真实标签predict_labels = zeros(1,people_num); %用于OVO后续投票% SVM网络预测for t = 1:1:model_numpredict_label = predict(eval(['model_' num2str(t)]),test_img');% test = [test,predict_label]; % 测试用predict_labels(1,predict_label) = predict_labels(1,predict_label) + 1;end[max_value,index] = max(predict_labels);if(index == test_real_label)right_num = right_num + 1; endendrecognition_rate = right_num / (test_pic_num_of_each * people_num); rate = [rate,recognition_rate];end

2.2 OVR实现SVM

% SVM(OVR)rate = []; %用于记录人脸识别率for i = 10:10:160right_num = 0;% 降维得到投影矩阵project_matrix = eigen_vectors(:,1:i);projected_train_data = project_matrix' * (train_data - all_mean);projected_test_data = project_matrix' * (test_data - all_mean);model_num = 1;% SVM训练过程(每次训练都要使用整个数据集)for j = 0:1:people_num - 1train_imgs = circshift(projected_train_data,-j * train_pic_num_of_each ,2); %使训练集始终在前几行train_label1 = ones(1,train_pic_num_of_each) * (j + 1);train_label2 = zeros(1,train_pic_num_of_each * (people_num - 1));train_label = [train_label1,train_label2];test_imgs = circshift(projected_test_data,-j * test_pic_num_of_each ,2); %使测试集始终在前几行% 数据预处理,将训练集和测试集归一化到[0,1]区间 [mtrain,ntrain] = size(train_imgs); %m为行数,n为列数[mtest,ntest] = size(test_imgs);test_dataset = [train_imgs,test_imgs];% mapminmax为MATLAB自带的归一化函数[dataset_scale,ps] = mapminmax(test_dataset,0,1);train_imgs = dataset_scale(:,1:ntrain);test_imgs = dataset_scale( :,(ntrain+1):(ntrain+ntest) );% SVM网络训练train_imgs = train_imgs';train_label = train_label';expr = ['model_' num2str(model_num) ' = fitcsvm(train_imgs,train_label);']; % fitcsvm默认读取数据为按行,一张一脸为一列,需要转置eval(expr);model_num = model_num + 1;endmodel_num = model_num - 1;% 人脸识别for k = 1:1:test_pic_num_of_each * people_numtest_img = projected_test_data(:,k); % 取出待识别图像test_real_label = fix((k - 1) / test_pic_num_of_each) + 1; % 给定待测试真实标签predict_labels = zeros(1,people_num); %用于OVR预测% SVM网络预测for t = 1:1:model_num[predict_label,possibility] = predict(eval(['model_' num2str(t)]),test_img');if predict_label ~= 0predict_labels(1,predict_label) = predict_labels(1,predict_label) + possibility(1,1); endend[min_value,index] = min(predict_labels); % 若一张图片被预测为多类,选择离超平面最远的作为最终预测类if(index == test_real_label)right_num = right_num + 1; endendrecognition_rate = right_num / (test_pic_num_of_each * people_num); rate = [rate,recognition_rate];end

3.PCA与LDA分别结合SVM在各维度、各数据集的人脸识别率及其与KNN的对比

运行SVM.m,比较在ORL(或其他数据集下)SVM(OVO实现为例)+降维方法与KNN+降维方法的人脸识别率随维度的变化,并在多个数据集下比较不同方法的人脸识别率,结果与分析如下:

3.1 ORL下比较SVM与KNN对于PCA和LDA的人脸识别率随维度的改变

3.2各种方法在不同数据集下的平均人脸识别率

Tips:数据集后为训练集与测试集的划分比

分析:分析以上两组图可知,各方法的人脸识别率与维度、数据集、参数选择均存在巨大关系,并没有某种方法组合在所有维度所有数据集下均具有优越性。

4.OVO与OVR实现SVM的人脸识别率比较

分别用OVO与OVR的思想训练SVM不同分类器并应用于人脸识别,在不同维度、不同数据集下的人脸识别率如下:

4.1ORL下比较OVO与OVR实现SVM + PCA的人脸识别率随维度的改变

4.2OVO与OVR实现SVM + PCA在不同数据集下的平均人脸识别率

分析:分析以上两组图可知,OVR实现SVM时在低维度时识别率低于OVO实现SVM,随着维度增加,OVR的识别率逐渐稳定地优于OVO,且在实验的三个数据集中,OVR的平均识别率均高于OVO。另外,OVR训练的分类器数量少,在小数据集下效率更高,但随着数据规模增大,OVR每次训练数据过大,效率会逐渐低于OVO。

5.方法与函数的补充

对于多分类SVM,matlab可以使用fitcecoc函数,python可以使用svm.SVC搭配fit与predict直接实现多分类SVM,而不需要多次训练二分类SVM。

四、创新SVM算法设计

① 经典SVM不足:无法处理非线性数据,对大规模训练样本难以实施。

② 已有改进:软间隔SVM/核SVM/ CSVM等

③ 创新SVM算法简述:

(1)SMO后通过对核函数的缓存可以大大增加算法效率。因为在经典SVM中,空间消耗主要在模型的训练,时间消耗主要在各种核函数与其他模型、函数的调用。

(2)对于最优化问题中f(x)的计算需要不断循环,代价很高,在此定义并缓存一个g(x)如下,让我们可以随时计算误差:

(3)优化数据集划分,实现冷热数据分离。热数据在前(大于0小于C的alpha值),冷数据在后(小于等于0 或者大于等于 C 的alpha)在后。随着迭代加深,大部分时候只需要在热数据里求解,并且热数据的大小会逐步不停的收缩,所以区分了冷热以后SVM 大部分都在针对有限的热数据迭代。

(4)传入外部分类“权重”修正结果,提高识别率。用原始的 C 乘以各自分类的权重,得到 Cp 和 Cn,然后迭代时,不同的样本根据它的 y 值符号,用不同的 C 值带入计算。

(5)同时支持稀疏和非稀疏,针对不同数据,选择合适的方式求解。

五、其他

1.数据集及资源

本实验所用数据集:ORL5646、AR5040、FERET_80,代码框架可适用多个数据集。

常用人脸数据集如下(不要白嫖哈哈哈)

链接:/s/12Le0mKEquGMgh5fhNagZGw

提取码:yrnb

SVM完整代码与二分类所需数据集:李忆如/忆如的机器学习 -

2. 参考资料

1.支持向量机(SVM)的推导(线性SVM、软间隔SVM、Kernel Trick) - liuyang0 - 博客园

2.手撕SVM公式——硬间隔、软间隔、核技巧_Dominic_S的博客-CSDN博客_硬间隔

3.手写SVM算法(Matlab实现) - 知乎 ()

4.SVM支持向量机+实例展示_Snippers的博客-CSDN博客_svm支持向量机

5.周志华《机器学习》

总结

SVM作为经典的线性二分类器,通过”最大化间隔“为目标导向对数据进行超空间(平面)投影并划分。如今仍然在机器学习许多领域(数据分类、语言图像处理、推荐系统)有优异表现。且作为一种有监督学习方法(利用了数据的原有信息),SVM能得到较好的保留数据信息。但SVM仍存在处理高维数据大计算代价问题、不好刻画非线性问题等等,另外,SVM假设的数据属性在现实世界的问题中往往难以达到,从而影响实验结果,后续博客会分析其他算法优化或解决上述问题。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。