本文将介绍一种基于深度学习和稀疏表达的人脸识别算法。首先,利用深度学习框架 (VGGFace) 提取人脸特征;其次,利用 PCA 对提取的特征进行降维;最后,利用稀疏表达分类实现特征匹配。我采用 CMC 曲线评价在 AR 数据库上的识别性能。最后我还提供了整个过程的 code。
下面介绍利用 VGGFace 对人脸特征进行提取。我们利用的数据库为 AR 数据库,数据库的图例如下:
接下来我们利用 VGGFace 对人脸特征进行提取。
利用 pca 对数据降维,VGGFace 提取出的特征为 4096 维,对提取的特征进行降维最后降到 128 维。
数据库一共有
其中
为稀疏编码。
最后我们可以利用稀疏表达分类器来识别这个 probe 人脸
:
- function cnn_vgg_faces()
- %CNN_VGG_FACES Demonstrates how to use VGG-Face
- clear all
- clc
- addpath PCA
- run(fullfile(fileparts(mfilename('fullpath')),...
- '..', 'matlab', 'vl_setupnn.m')) ;
- net = load('data/models/vgg-face.mat') ;
- list = dir('../data/AR');
- C = 100;
- img_list = list(3:end);
- index = [1, 10];
- %% 建立基于VGGFace的Gallery字典
- dictionary = [];
- for i = 1:C
- disp(i)
- numEachGalImg(i) = 0;
- for j = 1:2
- im = imread(strcat('../data/AR/',img_list((i-1)*26+index(j)).name));
- im_ = single(im) ; % note: 255 range
- im_ = imresize(im_, net.meta.normalization.imageSize(1:2)) ;
- for k = 1:3
- im1_(:,:,k) = im_;
- end
- im2_ = bsxfun(@minus,im1_,net.meta.normalization.averageImage) ;
- res = vl_simplenn(net, im2_) ;
- feature_p(:,j) = res(36).x(:);
- end
- numEachGalImg(i) = numEachGalImg(i) + size(feature_p,2);
- dictionary = [dictionary feature_p];
- end
- %% PCA对特征进行降维
- FaceContainer = double(dictionary');
- [pcaFaces W meanVec] = fastPCA(FaceContainer,128);
- X = pcaFaces;
- [X,A0,B0] = scaling(X);
- LFWparameter.mean = meanVec;
- LFWparameter.A = A0;
- LFWparameter.B = B0;
- LFWparameter.V = W;
- imfo = LFWparameter;
- train_fea = (double(FaceContainer)-repmat(imfo.mean, size(FaceContainer,1), 1))*imfo.V;
- dictionary = scaling(train_fea,1,imfo.A,imfo.B);
- for i = 1:size(dictionary, 1)
- dictionary(i,:) = dictionary(i,:)/norm(dictionary(i,:));
- end
- dictionary = double(dictionary);
- totalGalKeys = sum(numEachGalImg);
- cumNumEachGalImg = [0; cumsum(numEachGalImg')];
- %% 利用稀疏编码进行特征匹配
- % sparse coding parameters
- if ~exist('opt_choice', 'var')
- opt_choice = 1;
- end
- num_bases = 128;
- beta = 0.4;
- batch_size = size(dictionary, 1);
- num_iters = 5;
- if opt_choice==1
- sparsity_func= 'L1';
- epsilon = [];
- elseif opt_choice==2
- sparsity_func= 'epsL1';
- epsilon = 0.01;
- end
- Binit = [];
- fname_save = sprintf('../results/sc_%s_b%d_beta%g_%s', sparsity_func, num_bases, beta, datestr(now, 30));
- AtA = dictionary*dictionary';
- for i = 1:C
- fprintf('%s \n',num2str(i));
- tic
- im = imread(strcat('../data/AR/',img_list((i-1)*26+26).name));
- im_ = single(im) ; % note: 255 range
- im_ = imresize(im_, net.meta.normalization.imageSize(1:2)) ;
- for k = 1:3
- im1_(:,:,k) = im_;
- end
- im2_ = bsxfun(@minus,im1_,net.meta.normalization.averageImage) ;
- res = vl_simplenn(net, im2_) ;
- feature_p = res(36).x(:);
- feature_p = (double(feature_p)'-imfo.mean)*imfo.V;
- feature_p = scaling(feature_p,1,imfo.A,imfo.B);
- feature_p = feature_p/norm(feature_p, 2);
- [B S stat] = sparse_coding(AtA,0, dictionary', double(feature_p'), num_bases, beta, sparsity_func, epsilon, num_iters, batch_size, fname_save, Binit);
- for m = 1:length(numEachGalImg)
- AA = S(cumNumEachGalImg(m)+1:cumNumEachGalImg(m+1),:);
- X1 = dictionary(cumNumEachGalImg(m)+1:cumNumEachGalImg(m+1),:);
- recovery = X1'*AA;
- YY(m) = mean(sum((recovery'-double(feature_p)).^2));
- end
- score(:,i) = YY;
- toc
- end
- accuracy = calrank(score1,1:1,'ascend');
- fprintf('rank-1:%d/%%\n',accuracy*100);
文中以
calrank 可以计算得到 CMC 曲线:参见。
最后得到 rank-1 为 82%。
整个代码见资源,由于 vgg-face 太大,可以自己到 vgg 的官网下载,然后放到../matconvnet-1.0-beta19\examples\data\models 中。
来源: http://www.bubuko.com/infodetail-2250796.html