---
# System prepended metadata

title: Hand Posture Recognition with CNN -  以CNN解決手勢辨識問題
tags: [' CSIE', Fundamental Deep Learning Assignments 2019, ' NDHU']

---

---
title: Hand Posture Recognition with CNN -  以CNN解決手勢辨識問題
tags: Fundamental Deep Learning Assignments 2019, NDHU, CSIE
lang: zh_tw
---
# Hand Posture Recognition with CNN -  以CNN解決手勢辨識問題

##### Table of Contents
[TOC]

[code]: https://github.com/how8570/Hand-Posture-Recognition-with-CNN
## 0x00. Before Start - 在開始之前

- 環境建置
  參考自 [林鈺錦大大分享的環境配置](https://hackmd.io/@abc1236762/HJAozs9pB) 以及我自行需要的套件
    ```shell
    conda create -n deeplearn --strict-channel-priority python=3.6 
          tensorflow-gpu=1.14 keras numpy=1.16 pydot opencv
          jupyter pylint autopep8 matplotlab pillow scikit-learn
    ```
- [完整原始碼][code]
  > 這次我們用上了熟悉的 keras 套件完成 CNN 分類辨識問題。在這次的實作中要求，是利用 CNN 分辨出三種不同的手勢。
  >[name=how8570]

## 0x01. Problem Descriptions - 問題解釋
- 本次的作業來自 **東華大學2019年度的深度學習導論** 的課堂作業
- [這裡是原題 \[可能需要 東華e學院 帳號才能存取\] ](http://web.csie.ndhu.edu.tw/ccchiang/Data/fdl_assignment2.pdf)
- 問題描述： (來自原題)<br>![](https://i.imgur.com/v6kEClS.png)
  [資料集 \[可能需要 東華e學院 帳號才能存取\]](http://web.csie.ndhu.edu.tw/ccchiang/Data/All_gray_1_32_32.rar)
    
## 0x02. Solutions - 解決思路

- 由於這次我們很開心的可以使用套件了 ~~所以當然是先 import keras~~
  所以這的最大問題當然是在資料前處理的部分了
- 因為資料要分成測試跟訓練的部分，然後我檢查了一下資料集的數量
  ![](https://i.imgur.com/YAjnX29.png)
  摁...有點少阿...
- 於是為了增加資料量我在處理圖片時增加了 <U>**垂直鏡像**</U> 的處理
  實作如下
    ```python=
    def get_train_datas():
    train_data = []
    train_label = []

    for gen_path in itertools.product(path_of_TrainSets, path_of_type, path_of_dataID):
        path = 'All_gray_1_32_32/' + '/'.join(gen_path) + '/'
        for img in os.listdir(path):
             if img.endswith('jpg'):
                path += img
                train_data.append(mpimg.imread(path))
                # 垂直鏡射增加資料集
                train_data.append(mpimg.imread(path)[:,::-1])


        if gen_path[1] in ('0000', '0001', '0002'):
            train_label.append(0)
            train_label.append(0) # 別忘了一次是生兩張圖 label 也要加兩次
        elif gen_path[1] in ('0003', '0004', '0005'):
            train_label.append(1)
            train_label.append(1)
        elif gen_path[1] in ('0006', '0007', '0008'):
            train_label.append(2)
            train_label.append(2)

    return  np.array(train_data),  np.array(train_label)
    ```
- 模型設計部分
  ![](https://i.imgur.com/g3yRtKd.png)
  我以兩層捲積 (Conv2D) 連上三層的全連接層 (Dense) 的架構建置該模型，並在其中插入池化 (Maxpooling) 以期望更良好的抓取特徵，插入丟棄層 (Dropout) 以避免過度學習 (Overfitting)。
- 其他細節請參考 [完整原始碼](code)
## 0x03 Result - 實現成果
- 雖然在我寫作業之前，同寢室的同學一直跟我嚷嚷著他的 **訓練成果是 1** ，如此誇張之高。雖然第一時間覺得是 Overfitting，但讓我心裡備感壓力。
    - 而在最初還沒有增加資料時時做辨識率大概只有 83%~85% ，讓我直懷疑我以前在修其他課程所學到的經驗是不是有些出入？
    - 於是我就去向其他人請教他們的 code 怎麼樣的一回事，發現大部分的同學好像都誤會於老師的題目要求 (或是是我誤會？)
    - 他們在使用 fit 函數時，將 validation_data 的參數置入 (test_data, vali_label) 
      範例:`model.fit(x, y, validation_data=(test_data, vali_label), ...)`
      這也意味著這些測試資料並不是被用來測試的。
      上方的意思如果用比喻來說的話，那就是：
    - 1.我們訓練 小明 考數學 目標考到100分
      2.給了小明考古題 (有題目/有答案)
      3.考另一個題庫出的小考 (小考內容是類似的題目，但不曾出現在考古題中)，並告訴小明，這題你寫對了還是寫錯了。
      4.重複3.直到設定的次數
    - 但是這過程中其實已經讓小明 **類似利用試錯法** 的方式 **得知這些題庫小考題目解法**，及意味著 **如果有辦法訓練到 1.0，通常是 Overfitting**。( [issue 連結](https://github.com/keras-team/keras/issues/1753) 有提到相關內容)
    - 這樣可能導致我們在訓練模型時選出過度符合這些資料集(訓練+測試)的模型
- 關於我理解的 test_data 的使用方式
    - 我們應該是把 train_data 分成 train_feature 與 vali_features 兩個部分。訓練完模型後再使用 test_data 這份全新的考題來校驗我們的 model 的準確率
    - 而我使用這個方式來核對我的模型正確率如下：
      左邊是 loss 右邊是 正確率
      ![](https://i.imgur.com/DMx3czZ.png)
    - 雖然數字看起來低了不少，但我認為這才是 **真正有意義的正確率** ，不是唬爛的數字
    - 詳情疑問可以參考這邊 
        - [issue (多數支持放心在 validation_data 使用 test data)](https://github.com/keras-team/keras/issues/1753) 
        - [簡書上的內容 (支持不應該使用)](https://www.jianshu.com/p/0c7af5fbcf72)
- 圖片的部分
  ![](https://i.imgur.com/He91Cet.png )

    
## 0x04 Summary - 後計與總結
- 在嘗試鏡像原始資料集時，原本預期可能效果沒有這麼好，畢竟右手拇指會在左邊，手整個方向會不一樣。沒想到卻還是提升了不少準確率，可見對於 model 的特徵抽取來說，拇指在哪似乎不是這麼重要 ~~，可以把它切了~~。
- 雖然這次的作業好像砲火猛烈 XD ，但我覺得好像真的是大家誤會了題目的意思。

## 0x05 Tools and Reference - 工具與參考項目
- Tools
    - IDE: [Visual Studio Code](https://code.visualstudio.com/)
    - Git Remote repository: [GitHub](https://github.com/)
- Reference
    - lecture slide
    - [Wikipedia](https://www.wikipedia.org/)
    - [keras 中文 doc](https://keras.io/zh/)
    - [簡書](https://www.jianshu.com/)
> [name=how8570]
> [time=Thu, Dec 19, 2019 3:37 AM]

<style>
span.hidden-xs:after {
    content: ' × NDHU AI' !important;
}
</style>