利用tensorflow實現人臉驗證(face verification)的過程

一.前言

這一學期一直在學tensorflow框架,和深度學習的知識,重點是學卷積神經網絡。因爲只學理論的知識太枯燥無味,於是我就找了一個應用點,人臉識別。前幾天隨便逛谷歌學術的時候無意看到一篇關於人臉識別的文章,Deep Learning Face Representation from Predicting 10,000 Classes》,於是乎自己就想參考這篇文章利用之前學過的卷積神經網絡CNN基礎和自己愛好的Python語言嘗試做一個人臉識別系統。經查很多資料後,發現圖像處理需要運用到部分Opencv的知識,所以就先補了下Opencv的知識。最終自己在pc端做了一個系統,在數據集測試準確率可達96%,但是在實際環境下利用電腦鏡頭準確率比較低。

二.實現過程

2.1.模型的選取

選取的模型爲《Deep Learning Face Representation from Predicting 10,000 Classes》這篇論文所提到的卷積神經網絡,模型圖如下:

 

 

5層網絡,越往上的神經元的個數就越少,到最後就剩下160個神經元的輸出,上面的Face patches 是進過對齊過後的的人臉塊,也就是說已左(右)眼爲中心的人臉區域塊,嘴角爲中心的人臉區域塊等等,這樣就有多個不同的輸入塊輸入到CNN中,文章採用了把倒數第二層的輸出+倒數第一層的輸出作爲特徵(這應該是採用12年的Le Cun 那篇文章的track)。最後再把不同的塊所輸出的特徵連接起來,就形成了一個最終一張人臉的特徵。然後再用各種分類器對其特徵進行分類。採用Max-Pooling,softmax;

輸入圖像:39*31*k 個人矩形臉圖像塊+31*31*k(這裏k在彩色圖像時爲3,灰度時k爲1)個人臉正方形塊(因爲後面要考慮到是全局圖像還是局部圖像,且需要考慮到尺度問題),使用ReLU非線性處理;

以上是這個模型的說明,當然我只是參考了這個模型,在實際運用過程中稍做了修改。

2.2數據集的處理

我利用的數據集是celebFaces,其包含10,177個名人身份的202,599張人臉圖片,每張圖片都做好了特徵標記,包含人臉bbox標註框、5個人臉特徵點座標以及40個屬性標記,CelebA由香港中文大學開放提供,廣泛用於人臉相關的計算機視覺訓練任務,可用於人臉屬性標識訓練、人臉檢測訓練以及landmark標記等,官方網址:Large-scale CelebFaces Attributes (CelebA) Dataset

利用python將數據集劃分爲訓練集,驗證集,測試集。其中訓練集包括1109個人的99810張圖片,驗證集包括1109個人的11090張圖片,測試集包含2760對人臉照片,有的一對是同一個人(用1表示),有的不是同一個人(用0表示)。

2.3訓練模型

將訓練集數據以一批20張圖片輸入模型中,每張圖片的大小爲55*47*3。設置迭代次數爲50000次,學習率爲0.0001。經過四層卷積層,一層全連接層(特徵層),一層softmax分類輸出層輸出後的值與標籤值做比較,利用代價函數交叉熵,梯度下降法,來更新權值w,b。經過50000次迭代,在驗證集上的準確率達到99%,保存模型參數。其中前三層卷積層有最大池化層,第四層卷積層經過激活函數relu(線性修正單元函數)和第三層最大池化層作爲特徵層的輸入。部分代碼見附錄

2.4模型測試

測試模型時,輸入的是2760對人臉圖片,將特徵層的結果作爲輸出層,對測試集數據,利用訓練好的網絡提取特徵,因此每一張人臉用160維特徵向量表示,計算每一對人臉的距離,此距離我們用餘弦距離表示。得出判別是否同一個人的結果。餘弦距離定義爲:

餘弦相似性通過測量兩個向量的夾角的餘弦值來度量它們之間的相似性。0度角的餘弦值是1,而其他任何角度的餘弦值都不大於1;並且其最小值是-1。從而兩個向量之間的角度的餘弦值確定兩個向量是否大致指向相同的方向。兩個向量有相同的指向時,餘弦相似度的值爲1;兩個向量夾角爲90°時,餘弦相似度的值爲0;兩個向量指向完全相反的方向時,餘弦相似度的值爲-1。這結果是與向量的長度無關的,僅僅與向量的指向方向相關。餘弦相似度通常用於正空間,因此給出的值爲0到1之間。公式如下


經過測試準確率達到96%

2.5實現人臉識別系統

首先利用opencv和電腦攝像頭採集試驗室同學作爲人臉數據庫。在測試時,利用電腦攝像頭拍下的圖片與庫中的人臉圖片經過訓練好的模型提取特徵後做餘弦距離計算,若距離小余0.48則爲同一個人並在框標記出名字。經過實測準確率較低,還有待提高。最後效果見附錄

三.總結

對實測環境下準確率不高我認爲有以下幾點原因:

問題一:數據採集偏差。基於網絡採集的人臉數據集存在偏差。這些偏差表現在:1,個體之間照片數量差異很大;2,大部分採集的照片都是:微笑,化妝,年輕,漂亮的圖片。這些和真實場景中差異較大,因此在現實場景中準確率很低。
問題二:模型測試加陽性率非常低,但是現實應用中,人們更關注真陽性率。
問題三:人臉圖片的角度,光線,閉合(開口、閉口)和年齡等差異相互的作用,導致人臉識別系統現實應用準確率很低。

過程中遇到的問題和收穫:

過擬合的現象。訓練的epoch太高,模型測試反而準確率不高,說明模型出現了過擬合的問題。因此訓練的數據樣本需要足夠多, 增加樣本類別和樣本數,需要花費很多精力和時間;也可以調整模型,在神經網絡每一層的輸入數據進行Batch Normalization(數據歸一化),有利於數據的高效性,防止神經元的激勵函數鈍化實效 ,但是在樣本數量比較小的時候同樣不是很顯著。

自己在對數據集製作的操作中摸索了很久,查了很多資料,對Python的文件操作os模塊有了進一步的瞭解,以及對Opencv圖像處理有初步的理解和運用。


 效果圖:

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章