SVM+hog特徵實現手勢識別
上一篇寫到了SVM, 自己也花了大量的時間去看了原理。。。但總覺得沒有示例的話還是有點虛。同時也一直想要做一個手勢分類的項目玩。那趁自己還沒有忘記,趕緊把項目給搞了,順帶鞏固一下知識。使用MATLAB實現。
前提知識:
需要了解:
hog特徵:https://blog.csdn.net/yuanjiteng/article/details/99608311
SVM分類的基本原理:https://blog.csdn.net/yuanjiteng/article/details/99413090
MATLAB使用到的函數解析:
1. imageDatastore
imageDatastore:imds = imageDatastore('./images', 'IncludeSubfolders', true, 'labelsource', 'foldernames')
創建一個圖像數據儲存體以處理圖像集
其中第一個屬性可以是文件名,可以是圖片文件夾路徑,可以是所有文件
第二個參數:‘IncludeSubfolders’ 是否包括子文件夾 、true/false 子文件夾遞歸/不遞歸(recusively)
參數:FileExtensions’,EXTENSIONS 要包括的文件的擴展名,比如“.png”,".jpg"
參數:‘ReadSize’,READSIZE 調用讀取函數時要讀取的圖像文件數。默認情況下,讀取大小爲 1。
參數:‘LabelSource’,SOURCE LABELS 指定標籤來源,默認是無,是’foldernames’就是文件夾名稱做標籤
參數:‘Labels’ LABELS 指定數據存儲標籤,LABELS是一數組或向量。
imd屬性:Files ReadSize ReadFcn Lables
可以對imd執行的操作函數:
read - 讀取下一個連續文件
reset - 將數據存儲重置爲數據的開頭
preview - 從數據存儲讀取第一個圖像
readimage - 從數據存儲讀取指定圖像
readall - 從數據存儲讀取所有圖像文件
partition - 返回表示單個 原始數據存儲的分區部分
numpartitions - 返回合理數量的估計值分區與分區函數一起使用,
countEachLable - 計數圖像數據存儲中的唯一標籤的數量
有一個很重要的 [imds1,imds2] = splitEachLabel(imds, p); p爲小數代表百分比,p爲整數代表從該整數分
-
extractHogFeatures
提取hog特徵 使用方法 其中獲得的features就是hog特徵矩陣:
features = extractHOGFeatures(I)
[features, validPoints] = extractHOGFeatures(I, points)
%這個用法瞭解不多,對特殊的點求特徵值
[..., visualization] = extractHOGFeatures(I, ...)
%一般而言使用這個,optionally returns a HOG feature visualization that can be shown using plot(visualization)
[...] = extractHOGFeatures(..., Name, Value)
其中可以設置參數和值:
CellSize 默認是[8,8]
BlockSize 默認是[2,2]
BlockOverlap 默認 ceil(BlockSize/2)
‘NumBins’ 默認9
‘UseSignedOrientation’ 默認false 代表0-180°,true就是-180-180°
使用案例:
I1 = imread('gantrycrane.png'); [hog1, visualization] = extractHOGFeatures(I1,'CellSize',[32 32]); subplot(1,2,1); imshow(I1); subplot(1,2,2); plot(visualization);
-
fitcecoc 這個是MATLAB自帶的分類函數 用libsvm的自己瞭解
用法:
OBJ=FITCECOC(TBL,Y)
TBL就是數據集向量 Y是標籤 返回object 1v1方法關於MATLAB其他多分類可以參考:https://cloud.tencent.com/info/b061682362bea1b7040237c09413d437.html
分類matlab代碼
clear;clc
imdsTrain= imageDatastore('./trainimages', 'IncludeSubfolders', true, 'labelsource', 'foldernames');
%這裏選擇自己的文件夾路徑,我的是文件夾trainimages裏面含有left right 等圖片文件夾
imdsTest = imageDatastore('./Test1'); %測試文件夾路徑
Train_disp = countEachLabel(imdsTrain);
imageSize = [256,256];% 對所有圖像進行此尺寸的縮放
image1 = readimage(imdsTrain,1);
scaleImage = imresize(image1,imageSize);
[features, visualization] = extractHOGFeatures(scaleImage);%獲取feature的大小
numImages = length(imdsTrain.Files)%獲取訓練圖片數
featuresTrain = zeros(numImages,size(features,2),'single'); %構造矩陣
for i = 1:numImages
imageTrain = readimage(imdsTrain,i);
imageTrain = imresize(imageTrain,imageSize);
featuresTrain(i,:) = extractHOGFeatures(imageTrain);
end %獲取所有features 存儲在featuresTrain中
trainLabels = imdsTrain.Labels; %訓練標籤
%開始訓練並驗證
classifer = fitcecoc(featuresTrain,trainLabels);
cvecoc = crossval(classifer);
oosLoss=kfoldLoss(cvecoc);
%%預測
numTest = length(imdsTest.Files);
for i=1:numTest
testImage = readimage(imdsTest,i);
scaleTestImage = imresize(testImage,imageSize);
featureTest = extractHOGFeatures(scaleTestImage);
[predictIndex,score] = predict(classifer,featureTest);
figure;
imshow(testImage);
title(['predictImage: ',char(predictIndex)]);
end
運行結果
oosLoss=0.0806 分類結果還行,可以接受。
如果想要進一步把訓練的
MATLAB的.mat文件 轉換爲.yml文件,從而可以在opencv打開,參考下面:
:https://www.jianshu.com/p/ad6a2f8a3fc8
總結
視覺圖像領域的函數使用起來總是非常的複雜,其中fitcecoc函數可以實現的功能很多,想要徹底瞭解其用法還是去MATLAB打開文件慢慢看吧。我這只是拿來練習一下svm的使用。
實現了圖片分類之後,下一步就應該是實現視頻的實時讀取和預測,其中又涉及到滑窗建立然後概率判斷問題,再有就是GPU的使用提高效率,具體就參看hog行人檢測代碼。實時手勢識別使用openpose在opencv實現或者yolo都是不錯的選擇。