2019年8月10日 星期六

[影像辨識] HOG圖片中人物偵測

圖片物體偵測

需要使用的演算法:
  1. 方向梯度圖譜 HOG(Histogram of Oriented Gradients)
  2. 影像金字塔 Image pyramids
  3. 窗格滑移 Sliding windows

方向梯度圖譜 HOG(Histogram of Oriented Gradients)

參考資料:
HOG與SIFT, SURF, ORB類似,都做圖片特徵描述 把圖片轉換成HOG的視野(pixel-->cell-->block):

1.計算圖片中每個pixel的梯度大小和角度:

將每個pixel分別對x方向Sobel filter和y方向Sobel filter做conolution,得到圖片在x方向和y方向的微分圖gx和gy
Screenshot%202019-08-09%2017.05.26.png
計算每個pixel的梯度大小和角度,若圖片為彩色,則梯度大小為三個channel中最大的那一個,角度則
為梯度最大的那個challel對應的角度
Screenshot%202019-08-09%2017.12.47.png
現在每一個pixel都有梯度大小和角度的資訊

2.計算cell內部的HOG:

把圖片切割成很多個cell(下圖中綠色格子為一個cell),每個cell由8*8個pixels組成.
Screenshot%202019-08-09%2017.07.34.png
每個cell裡面統計64個pixels在0-180度上的分佈圖譜,每個cell用一個histogram來描述特徵值.統計方式如下圖所示,若角度為10(紅色線),則將這個角度對應的梯度大小一比例分配到0和20的histogram.
Screenshot%202019-08-09%2017.17.27.png
若如下圖所示,角度為165度,則將梯度強度依比例分配到160和180(等效為0度)
Screenshot%202019-08-09%2017.22.04.png
依此類推對cell內每個pixel做統計histogram.

Screenshot%202019-08-09%2017.23.37.png

3. Block Normalization (block只用來做normalization, 不用來描述特徵值)

接下來把cell組成group(可以由任意數目的cell組成).Dalal 和 Triggs發現若要辨識人類,一個block內包含2x2個cell會比較好,group完後就可以組成block-wide vector,每個block-wide vectors內有9*4=36個vextor的histogram,對block內的block-wide vectors做L2 norm,做完normalization後將block向右滑動一格再做一次normlization...以此類推

Screenshot%202019-08-09%2017.35.40.png

3. 計算HOG特徵向量

下圖中共有8x16個cell, 而每個cell內的histogram有9個vector特徵值,所以這張圖總共有8x16x9=1152個維度的向量.這個做法有想像是把圖片做PCA降維到1152軸的空間向量.HOG descriptor可以想像是由HOG的視角來看這張圖片,由下圖所示.但是opevCV並沒有視覺化HOG descriptor的函數.HOG descriptor已經包含充足的圖片資訊可以有效地把圖片中物體得特徵值描述出來.
Screenshot%202019-08-09%2017.40.29.png
因為HOGdescriptor已經含有充足的資訊,因此我們也可以把HOG做逆向轉換,還原成原來的影像.MATLAB有內建的invertHOG函數可以將HOG descriptor還原成原來的影像,如下圖所示.
Screenshot%202019-08-09%2017.52.54.png

影像金字塔 Image pyramids

  1. 取一張影像
  2. 縮放影像
  3. 用高斯模糊來使影像平整
  4. 如果影像比設定的閥值大則重複第一個步驟
可以使用pyrDown()對圖像做down sampling
語法: img = cv2.pyrDown(cv2.imread("contour.jpg", cv2.IMREAD_UNCHANGED))
Opencv中可以通過函數cv2.pyrDown()和cv2.pyrUp()來構建金字塔。 函數cv2.pyrDown()是從一個高分辨率圖像變成低分辨率圖像的。
cv2.pyrDown()函數接受3個參數: tmp: 當前圖像,初始化為原圖像 src 。 dst: 目的圖像( 顯示圖像,為輸入圖像的一半) Size( tmp.cols/2, tmp.rows/2 ) :目的圖像大小, 既然我們是向下採樣 默認情況下直接輸入需要操作的圖像就可以,他會把圖像按縮小1/4的來處理
Screenshot%202019-08-09%2018.10.56.png

窗格滑移 Sliding windows

步驟如下圖所示,不斷地移動綠色窗格,並用classifier來做classification,依序將HOG map的每個cell都掃瞄過去,會取得每個掃描方格的分類機率具最大值.對每一層金字塔都做相同的步驟.因此可以得到非常多掃描窗格的預測值,只選取重複掃描區域預測最大的數值(Non-maximum (or non-maxima) suppression不是最大的就不要).
In [4]:
1
from IPython.display import display, Image, SVG, Math, YouTubeVideo
2
Image(url='https://www.pyimagesearch.com/wp-content/uploads/2014/10/sliding_window_example.gif')
3
Out[4]:

In [ ]:
1
#用HOG做圖形的編碼 + detectMultiScale(Image pyramids+Sliding windows) + SVM classifier
2
3
import cv2
4
import numpy as np
5
6
def is_inside(o, i):
7
   ox, oy, ow, oh = o
8
   ix, iy, iw, ih = i
9
   return ox > ix and oy > iy and ox + ow < ix + iw and oy + oh < iy + ih
10
11
def draw_person(image, person):
12
 x, y, w, h = person
13
 cv2.rectangle(img, (x, y), (x + w, y + h), (0, 255, 255), 2)
14
15
img = cv2.imread("../../people.jpg")
16
hog = cv2.HOGDescriptor()
17
hog.setSVMDetector(cv2.HOGDescriptor_getDefaultPeopleDetector())
18
found, w = hog.detectMultiScale(img, winStride=(3,3),scale=1.1)
19
found_filtered = []
20
for ri, r in enumerate(found):
21
   for qi, q in enumerate(found):
22
       if ri != qi and is_inside(r, q):
23
           break
24
   else:
25
       found_filtered.append(r)
26
27
for person in found_filtered:
28
 draw_person(img, person)
29
30
cv2.imshow("people detection", img) 
31
cv2.waitKey(0)
32
cv2.destroyAllWindows()
33

三倍槓桿和一倍槓桿的長期定期定額報酬率分析

  以下是中國,美國股票債卷的三倍槓桿和一倍槓桿ETF分析.可以發現,三倍槓桿在下跌時期的跌幅遠比一倍槓桿的多 .且從時間軸來看,三倍槓桿由於下跌力道較強,因此會把之前的漲幅都吃掉,所以對於長期上身的市場,例如美國科技股,由於上升時間遠比下跌時間長,所以持有TQQQ的長期回報率會...