---
# System prepended metadata

title: '1 YOLOv1: What''s YOLO doing?'
tags: [YOLO]

---

## One-stage / Two-stage Learning
一般作法是先用 Selective search 選出物件，這個過程稱為 Region proposal，接著對這些候選的物件進行辨識，這樣的流程稱作是 Two-stage learning。

其中，Two-stage learning 除非有很強的 GPU 運算資源，否則幾乎無法做到即時運算；而 One-stage learning 則代表物件位置和物件辨識一步到位，也就是透過一個神經網路能同時偵測位置和做分類。

* Two-stage: R-CNN、Fast R-CNN、Faster R-CNN
* One-stage: YOLOv1...YOLOv3、Tiny YOLO、SSD

One-stage learning 會先選出候選物件，再判斷候選物件是不是某類別，但有可能一個物件被很多候選框給選到，因此就會用 NMS 處理消除多餘物件框，找到最佳的框:

<div class="text-center">
    <img src="https://hackmd.io/_uploads/Bydu4ydDa.png" style="width: 600px; object-fit: cover;">
</div>

&nbsp;
選出來的框叫做 Bounding box，每一個框都具有:

* 中心座標 $(x,y)$
* 長寬 $(h,w)$
* Confidence: 前景（Foreground）或背景（Background）的信心程度
* 各類別機率


## Non-Maximum Suppression
假設只偵測 2 個物件，每個框具有 5+2=7 個維度；假設偵測 100 個物件，每個框則具有共 5+100=105 個維度。其中，NMS 操作步驟如下:

1. 先看哪個框的信心程度最高，將這個框加入「確定是物件的集合」內
2. 其他框和剛剛選出的框計算 IoU，算出的 IoU 若大於設定門檻，這些框的信心度會被設定為 0（也就是這個框已經重複計算，將其刪除）

範例 1: 有兩隻狗，如何用 NMS 將偵測到的物件框將把兩隻狗框出來

<div class="text-center">
    <img src="https://hackmd.io/_uploads/ryHhNJuwp.png" style="width: 700px; object-fit: cover;">
</div>

&nbsp;
假設 IoU 設定為 0.7 而非 0.5，會發生什麼事情呢?

<div class="text-center">
    <img src="https://hackmd.io/_uploads/BJlR41Ovp.png" style="width: 700px; object-fit: cover;">
</div>

&nbsp;
範例 2: 有一狗一貓，如何用 NMS 將偵測到的物件框將把貓和狗框出來

<div class="text-center">
    <img src="https://hackmd.io/_uploads/BkazH1OPp.png" style="width: 700px; object-fit: cover;">
</div>

&nbsp;
其實，在 NMS 的操作上完全相同，只是最後把選出來的再確認一下預測的類別是什麼。一般來說，物件偵測比較接近第二個範例，每個框還會有自己的分類機率。實務上，二階段偵測器會在第一步 Region proposal 時就先用 Confidence 門檻值去掉一些候選框，避免因篩選過多的框導致後續 NMS 的耗時問題。

<div class="text-center">
    <img src="https://hackmd.io/_uploads/SJGLHJuva.png" style="width: 700px; object-fit: cover;">
</div>

&nbsp;
此外，二階段偵測器預測的框只有中心座標、長寬和 Confidence，不含類別機率，因為順序是先選框，最後再將框出的 Feature map 做 Rescale（一般用 ROI pooling）和分類。


## Bounding box & Classification
YOLO 物件偵測是將圖拆成很多個 Grid cell，在每個 Cell 上進行 2 個框的位置和類別預測，最後再以 NMS 得到結果。==舉例來說，輸入影像大小為 100X100，總共偵測 C 個種類。輸出的 Tensor 大小是 SXSX(BX5+C):==

1. 假設 S=5，YOLO 把圖平均分成 5X5 格，每格為一個 20X20 的 Grid cell
2. 每個 Grid cell 負責預測「B 個 Bounding box」和「一個各類別的機率」
3. 每個 Bounding box 有 5 個資訊 $(x,y,w,h,confidence)$

以 PASCAL VOC 做 YOLO 為例: 設定 S=7、B=2，PASCAL VOC 有 20 個物件的類別，所以 C=20，因此最終輸出為 7X7X(2X5+20)=7X7X30。

<div class="text-center">
    <img src="https://hackmd.io/_uploads/rkUceMckyg.jpg" style="width: 700px; object-fit: cover;">
</div>

&nbsp;
1. YOLO 在整張圖共有 7X7=49 個Grid Cell，每個 Cell 做 2 個框的預測，所以全部的候選框共有 7X7X2=98 個，意即最多只嘗試找 98 個物件 
2. 每個 Cell 的輸出維度為 2X5+20=30
    * 2 代表二個框
    * 5 代表 $(x,y,w,h,confidence)$
    * 20 代表 20 個類別
3. 在每個 Cell 中的兩個框只共用一個類別預測，在訓練時會選和 GT IoU 比較大的框負責做位置和類別預測；測試時則是選取 Confidence 高的框、另一個會被捨棄，因此 7×7=49 個 Gird cell 最多只會預測 49 個物體
4. 總而言之，訓練時 98 個框都會參與 Loss 計算、但推論只會預測 49 個框

註: Confidence 即是預測框和GT（Ground truth）的 IoU。

<div class="text-center">
    <img src="https://hackmd.io/_uploads/rkAaxGq1Je.jpg" style="width: 700px; object-fit: cover;">
</div>

&nbsp;
1. 位置座標、長寬是用正規化後的結果，因此直接乘以比例即可計算真實位置和大小
2. NMS 只存在於預測，訓練不會用 NMS，因為 98 個候選框都和 Loss 相關不能捨棄
3. 預測階段是先將 98 個候選框以 Confidence 門檻先濾除背景（判斷為前景代表這裡有物件），再將所有屬於同一類的框去做 NMS


## YOLO 訓練細節
YOLO 的 Loss 包含以下三項:

* Location loss: 預測框和 GT 間的位置和長寬差異
* Object loss: 預測框是前景或背景
* Classification loss: 分類器是否將物件分類正確

以下針對各 Loss 進行說明:

1. Location Loss
    舉例來說，3X3 的 Grid 中有二個物件，會由第 i 個 Cell 的第 j 個框負責做預測，代表雖然有 1~9 個預測框，==但真正會計算 Location loss 的只有 5 號紅框和 7 號紅框==。此外，雖然 w 和 h 差值相同，但預測框在大物件的預測比較準確、小物件則較不準確:

    <div class="text-center">
        <img src="https://hackmd.io/_uploads/r105ZGckJl.jpg" style="width: 700px; object-fit: cover;">
    </div>

    ==因此作者將 w 和 h 的 Loss 作開根號修正==，讓小物件的差值放大，增加小物件判斷錯誤的 Loss，進而引導網路提升在小物件的預測效果:

    <div class="text-center">
        <img src="https://hackmd.io/_uploads/SJoPbGcJJl.jpg" style="width: 700px; object-fit: cover;">
    </div>

2. Object Loss
    以下圖為例，$C_i$ 是前景和背景的 GT、$\hat{C}_i$ 是框的預測值。可以看到 YOLO 中共有 98 個預測框，但是當 96 個框是背景、僅有 2 個框是前景的情況下，過多的背景 Loss 會主導 Graident descent，反而讓前景的學習效果變得較差:
    
    <div class="text-center">
        <img src="https://hackmd.io/_uploads/SkmJzM5J1g.jpg" style="width: 700px; object-fit: cover;">
    </div>

    作者在這邊很簡單的加入一個權重，降低背景學習的比重:
    
    <div class="text-center">
        <img src="https://hackmd.io/_uploads/S1TMMGq1Jl.png" style="width: ˙00px; object-fit: cover;">
    </div>

3. Classification Loss
    當 GT 的中心出現在第 i 個 Cell 時，該 Cell 中的預測才會負責做類別 Loss 的計算，也就是 5 號和 7 號預測框的類別才會拿來計算 Loss:
    
    <div class="text-center">
        <img src="https://hackmd.io/_uploads/rypNffcy1x.png" style="width: 700px; object-fit: cover;">
    </div>

總結以上，三項 Loss 表示如下:

<div class="text-center">
    <img src="https://hackmd.io/_uploads/ByODGMqJ1l.png" style="width: 700px; object-fit: cover;">
</div>


## Discussion of YOLO
由於 YOLO 受限於架構設計（輸出向量的限制），主要會有二項缺點:

1. 每個 Cell 只會取 Confidence 高的框做預測，假設有多個物體出現在同一個 Cell，YOLO 只能預測出一個而無法找到其他物件；其中，改善方式可以直接對輸出向量做修正，例如每個框都做分類預測:

    <div class="text-center">
        <img src="https://hackmd.io/_uploads/ryN3Gz51kl.png" style="width: 700px; object-fit: cover;">
    </div>

2. 對於在學習資料沒有出現過的長寬比，在 Location loss 可能也不會有很好的表現，這部分可以透過 Data augmentation 來解決:

    <div class="text-center">
        <img src="https://hackmd.io/_uploads/r1nCMfcyJx.png" style="width: 700px; object-fit: cover;">
    </div>


## Reference
* [圖解一階段物件偵測算法_Part01 - YOLOv1-重錄版](https://www.youtube.com/watch?v=sq_OfIhb5Oc&list=PLANbacZNzD9FOcLenvcfgE7R4QdHgOXSq&index=2&ab_channel=WilsonHo)
* [【YOLO系列】YOLOv1论文超详细解读（翻译 ＋学习笔记）](https://blog.csdn.net/weixin_43334693/article/details/129011644?spm=1001.2014.3001.5501)
* [深度學習-物件偵測:You Only Look Once (YOLO)](https://chih-sheng-huang821.medium.com/%E6%B7%B1%E5%BA%A6%E5%AD%B8%E7%BF%92-%E7%89%A9%E4%BB%B6%E5%81%B5%E6%B8%AC-you-only-look-once-yolo-4fb9cf49453c)
* [機器/深度學習: 物件偵測 Non-Maximum Suppression (NMS)](https://chih-sheng-huang821.medium.com/%E6%A9%9F%E5%99%A8-%E6%B7%B1%E5%BA%A6%E5%AD%B8%E7%BF%92-%E7%89%A9%E4%BB%B6%E5%81%B5%E6%B8%AC-non-maximum-suppression-nms-aa70c45adffa)
