1、目標定位(Object localization)
目標定位旨在識別影像或影片中的特定目標,並確定其在影像中的具體位置。目標定位的輸出通常包括目標所屬的類別(如果是分類任務)和一個邊界框(Bounding Box),該邊界框用於精確地描述目標在影像中的位置。因此先從分類和定位(classification with localization)開始講起。
如上圖,這是圖片分類問題,輸入一張圖片到多層卷積神經網路。這就是卷積神經網路,它會輸出一個特徵向量,並反饋給softmax單元來預測圖片型別。這就是標準的分類過程(classification pipeline),如果你還想定點陣圖片中汽車的位置,可以讓神經網路多輸出幾個單元,輸出一個邊界框。具體就是讓神經網路再多輸出4個數字,標記為b_x, b_y, b_h和b_w,這四個數字是被檢測物件的邊界框的引數化表示。
現在設定圖片左上角的座標為(0,0),右下角標記為(1,1)。要確定邊界框的具體位置,需要指定紅色方框的中心點(midpoint),這個點表示為(b_x,b_y),邊界框的高度為b_h,寬度為b_h。
下面具體看如何為監督學習任務定義目標標籤y,如下圖:
這有四個分類,神經網路輸出的是這四個數字和一個分類標籤,或分類標籤出現的機率。目標標籤y的定義如下:
這是一個向量,第一個p_c表示是否含有物件,在這裡如果物件屬於前三類(行人(pedestrian)、汽車(car)、摩托車(motorcycle)),則p_c=1,如果是背景(background),則圖片中沒有要檢測的物件,則p_c=0。我們可以認為它表示被檢測物件屬於某一類的機率,背景分類除外。如果檢測到物件,輸出被檢測物件的邊界框引數b_x,b_y,b_h和b_w,同時輸出c_1、c_2和c_3,表示該物件屬於1-3類中的哪一類(行人、汽車或者摩托車)。
最後看一下神經網路的損失函式(loss function)),引數為網路輸出y帽和類別y,採用平方誤差策略(squared error),則損失值等於每個元素相應差值的平方和,當y_1=1時,平方誤差策略為這8個元素預測值和實際輸出結果之間差值的平方。當y_1=0時,y中的後7個元素都不用考慮,只需要考慮神經網路評估yy_1(即p_c)的準確度。
注意一下,這裡用平方誤差簡化了描述過程,實際應用中,通常做法是對邊界框座標應用平方差或類似方法,對p_c應用邏輯迴歸函式,甚至採用平方預測誤差也是可以的。
2、特徵點檢測(Landmark detection)
神經網路也可以透過輸出圖片上特徵點的(x,y)座標來實現對目標特徵的識別,下面看幾個例子。
假設你正在構建一個人臉識別應用(face recognition application),你希望演算法可以給出眼角(其他臉部部位也同樣)的具體位置。眼角座標為(x,y),讓神經網路的最後一層多輸出兩個數字l_x和l_y,為眼角的座標值。選定特徵點個數,並生成包含這些特徵點的標籤訓練集(label training set),然後利用神經網路輸出臉部關鍵特徵點的位置。
具體做法是,準備一個卷積網路和一些特徵集,將人臉圖片輸入卷積網路,輸出1或0,1表示有人臉,0表示沒有人臉,然後輸出(l_1x,l_1y)......直到(l_64x,l_64y)。這裡一共有129(1+2*64=129)個輸出單元,由此實現對圖片的人臉檢測和定位。
再看一個例子,上圖的第三張圖,如果你對人體姿態檢測(people post-detection)感興趣,也可以定義一些關鍵特徵點(key positions),如胸部的中點(the midpoint of the chest),左肩(the left shoulder),左肘(left elbow),腰(the wrist)等,從胸部中心點(l_1x,l_1y)一直向下,一直到(l_32x,l_32y)。然後透過神經網路標註人物姿態的關鍵特徵點,再輸出這些標註過的特徵點,就相當於輸出了人物的姿態動作。要明確一點,特徵點的特性(identity)在所有圖片中必須保持一致,就好比,特徵點1始終是右眼的外眼角,特徵點2是右眼的內眼角等等。
3、目標檢測(Object detection)
學過了目標定位(object localization)和特徵點檢測(landmark detection),現在來構建一個目標檢測演算法。我們將學習如何透過卷積網路進行目標檢測,採用的是基於滑動視窗的目標檢測演算法(the sliding windows detection algorithm)。
假如在構建一個汽車檢測演算法,(1)首先建立一個標籤訓練集,也就是x和y表示適當剪下的汽車圖片樣本,前三張圖片是正樣本,因為它們是汽車圖片。(2)然後可以訓練卷積網路,輸入為這些適當裁剪過的圖片,輸出為y(0或1表示圖片中有汽車或沒有汽車)。(3)訓練完這個卷積網路,就可以用它來實現滑動視窗目標檢測,具體步驟如下:
這種演算法叫作滑動視窗目標檢測(sliding windows detection),因為以某個步幅滑動這些方框視窗遍歷整張圖片,對這些方形區域進行分類,判斷裡面有沒有汽車。滑動視窗目標檢測演算法有很明顯的缺點,就是計算成本。因為你在圖片中剪下出太多小方塊,卷積網路要一個個地處理。如果你選用的步幅很大,顯然會減少輸入卷積網路的視窗個數,但是粗糙間隔尺寸可能會影響效能。反之,如果採用小粒度或小步幅,傳遞給卷積網路的小視窗會特別多,這意味著超高的計算成本。
4、滑動視窗的卷積實現(Convolutional implementation of sliding windows)
為了構建滑動視窗的卷積應用,首先要知道如何把神經網路的全連線層轉化成卷積層。那麼為什麼要將全連線層轉化成卷積層?有以下原因:
以下是神經網路的全連線層轉化成卷積層的過程
總結一下滑動視窗的實現過程如下:
在原圖上剪下出一塊區域,假設它的大小是14×14,把它輸入到卷積網路。繼續輸入下一塊14×14區域,重複操作,直到某個區域識別到汽車。我們不能依靠連續的卷積操作來識別圖片中的汽車,我們可以對大小為28×28的整張圖片進行卷積操作,一次得到所有預測值,如果足夠幸運,神經網路便可以識別出汽車的位置。
以上就是在卷積層上應用滑動視窗演算法的內容,它提高了整個演算法的效率。不過這種演算法仍然存在一個缺點(weakness),就是邊界框的位置可能不夠準確。
5、Bounding Box預測(Bounding box predictions)
在上一個影片中,我們瞭解了滑動視窗法的卷積實現,這個演算法效率更高,但仍然存在問題,不能輸出最精準的邊界框。接下來看看如何得到更精準的邊界框。
如上圖,在滑動視窗法中,這些邊界框沒有一個能完美匹配汽車位置,也許右下角的藍框是最匹配的啦。甚至最完美的框(右下角的紅色框)不是正方形,而是長方形。
其中一個能得到更精準邊界框的演算法是YOLO演算法,YOLO(You only look once)意思是你只看一次,把物件分配到一個格子的過程是,將這個物件分配到其中點所在的格子,所以即使物件可以橫跨多個格子,也只會被分配到9個格子其中之一,就是3×3網路的其中一個格子,或者19×19網路的其中一個格子。在19×19網格中,兩個物件的中點(圖中藍色點所示)處於同一個格子的機率就會更低。
需要注意的是:(1)這和影像分類和定位演算法非常像,它顯式地輸出邊界框座標,能讓神經網路輸出邊界框,可以具有任意寬高比,並且能輸出更精確的座標,不會受到滑動視窗分類器的步長大小限制。(2)這是一個卷積實現,你並沒有在3×3網格上跑9次演算法,相反,這是單次卷積實現,但你使用了一個卷積網路,有很多共享計算步驟,在處理這3×3計算中很多計算步驟是共享的,所以這個演算法效率很高。事實上YOLO演算法有一個好處,也是它受歡迎的原因,因為這是一個卷積實現,實際上它的執行速度非常快,可以達到實時(real-time)識別。
6、交併比(Intersection over union)
如何判斷目標檢測演算法運作良好呢?在本影片中,你將瞭解到並交比(intersection over union)函式,可以用來評價目標檢測演算法。
交併比(loU)函式做的是計算兩個邊界框交集和並集之比。兩個邊界框的並集是這個區域,就是屬於包含兩個邊界框區域(綠色陰影表示區域),而交集就是這個比較小的區域(橙色陰影表示區域),那麼交併比就是交集的大小,這個橙色陰影面積,然後除以綠色陰影的並集面積。
一般來說,IoU大於等於0.5,那麼結果是可以接受的,就說檢測正確。如果預測器和實際邊界框完美重疊,loU就是1,因為交集就等於並集。一般約定,0.5是閾值(threshold),用來判斷預測的邊界框是否正確。loU越高,邊界框越精確。
7、非極大值抑制(Non-max suppression)
目前為止的目標檢測中可能出現的問題是你的演算法可能對同一個物件做出多次檢測。非極大值抑制(non-max suppression)這個方法可以確保你的演算法對每個物件只檢測一次。
當你在所劃分的格子上都執行一次影像檢測和定位演算法,最後可能會對同一個物件做出多次檢測,所以非極大值抑制做的就是清理這些檢測結果。這樣一輛車只檢測一次,而不是每輛車都觸發多次檢測。具體做法如下圖:
首先看機率最大的那個,這個例子(右邊車輛)中p_c是0.9,然後就說這是最可靠的檢測(most confident detection),所以我們就用高亮標記,表明這裡找到了一輛車。這麼做之後,非極大值抑制就會逐一審視剩下的矩形,所有和這個最大的邊框有很高交併比,高度重疊的其他邊界框,那麼這些輸出就會被抑制。所以這兩個矩形(p_c分別是0.6和0.7),和淡藍色矩形重疊程度很高,所以會被抑制,變暗,表示它們被抑制了。
接下來,逐一審視剩下的矩形,找出機率最高,p_c最高的一個,在這種情況下是0.8,如上圖,我們就認為這裡檢測出一輛車(左邊車輛),然後非極大值抑制演算法就會去掉其他loU值很高的矩形。非最大值意味著你只輸出機率最大的分類結果,但抑制很接近,但不是最大的其他預測結果,所以這方法叫做非極大值抑制。
8、錨(Anchor Boxes)
到目前為止,目標檢測中存在的一個問題是每個格子只能檢測出一個物件,如果想檢測出多個物件,可以使用anchor box這個概念。錨點框本質上是一些預定義的邊界框模板,它們在模型預測過程中提供了一個初始參考框架,用來擬合影像中的目標物體。透過這些錨點框,目標檢測模型可以處理同一影像中的多個物體,不同的尺度和長寬比。
對於這張圖片,繼續使用3×3網格,注意行人的中點和汽車的中點幾乎在同一個地方,兩者都落入到同一個格子中。在檢測這三個類別(行人、汽車和摩托車)時,它將無法輸出檢測結果,所以必須從兩個檢測結果中選一個。
現在模型不僅僅根據物體的中心將其分配到某個網格單元,還會進一步透過錨點框的大小和形狀來擬合物體的邊界框(透過交併比選擇)。這種組合(網格單元和錨點框)作為一個整體來對物體進行編碼和預測,使得模型能夠處理不同大小和形狀的物體,更好地完成目標檢測任務。最終的輸出張量 y 包含多個資訊:每個網格單元中的多個錨點框的預測結果。輸出的維度取決於網格的大小、每個網格的錨點框數量,以及每個錨點框預測的類別和位置。
以上就是anchor box的概念,anchor box是為了處理兩個物件出現在同一個格子的情況,實踐中這種情況很少發生,特別是如果你用的是19×19網格而不是3×3的網格時。
最後,你應該怎麼選擇anchor box呢?人們一般手工指定anchor box形狀,你可以選擇5到10個anchor box形狀,覆蓋到多種不同的形狀,可以涵蓋你想要檢測的物件的各種形狀。後期YOLO論文中有更好的做法,就是所謂的k-平均演算法(k-means),可以將兩類物件形狀聚類,如果我們用它來選擇一組anchor box,選擇最具有代表性的一組anchor box,可以代表你試圖檢測的十幾個物件類別,但這其實是自動選擇anchor box的高階方法。