模式匹配方法總結及實現


一. 模式匹配簡介:

    模式匹配 ——> 尋找待匹配圖像和全體圖像中最相似的部分,常用於物體檢測任務。雖然現在使用卷積神經網絡做物體檢測任務有更好的效果,但是模式匹配是最基本的物體檢測方法,它很基礎,很重要。


二. 模式匹配算法:

    原圖像為 I(H  X  W),待匹配圖像為 T(h X w)。

    1. 對於圖像 I:,for j in range(H-h):for i in range(W-w) 。在一次移動一像素的過程中,計算原圖像的一部分 I[j:j+h,i:i+w] 與待匹配圖像 T 的相似度 S。

    注:像模式匹配這樣,從圖像的左上角開始向右順序進行查找的操作稱為光柵掃描(Raster Scan),或滑動窗口掃描(Sliding window)。

    2. S 最大或者最小的地方即為匹配到的位置。

        S 的計算方法主要有 SSD(Sum of Squared Difference:誤差平方和)、SAD(Sum of Absolute Differences:誤差絕對值和)、NCC(Normalization Cross Correlation:歸一化交叉相關)、ZNCC(Zero-mean Normalization Cross Correlation:零均值歸一化交叉相關),對於不同的方法,我們需要選擇出 S 的最大值或者最小值,然后找到 S 的值對應的在原圖像中的位置。


三. 不同的模式匹配標准(不同的 S)

        S = SSD(Sum of Squared Difference),S 取最小的值。


SSD(誤差平方和)最小 ↑
 

        python實現核心代碼:_v = np.sum((img[y:y+Ht, x:x+Wt] - temp) ** 2)


        S = SAD(Sum of Absolute Differences),S 取最小的值。


SAD(誤差絕對值之和)最小 ↑
 

        python實現核心代碼:_v = np.sum(np.abs(img[y:y+Ht, x:x+Wt] - temp))


        S = NCC(Normalization Cross Correlation),S 取最大的值。求出兩個圖像的相似度,S 的范圍為[-1,1],S 對變化十分敏感。


NCC(歸一化交叉相關)最大 ↑
 

  python實現核心代碼:_v = np.sum(img[y:y+Ht, x:x+Wt] * temp)

        _v /= (np.sqrt(np.sum(img[y:y+Ht, x:x+Wt]**2)) * np.sqrt(np.sum(temp**2)))


        S = ZNCC(Zero-mean Normalization Cross Correlation),S 取最大的值。它比歸一化交叉相關更加敏感。圖像 I 的平均值為 m_i,圖像 T 的平均值為 m_t。S 的范圍為 [-1,1]。


ZNCC(零均值歸一化交叉相關)最大 ↑
 

        python實現核心代碼:_v = np.sum((img[y:y+Ht, x:x+Wt]-mi) * (temp-mt))

            _v /= (np.sqrt(np.sum((img[y:y+Ht, x:x+Wt]-mi)**2)) * np.sqrt(np.sum((temp-mt)**2)))


四. python實現零均值歸一化交叉相關。不同的 S ,讀者可舉一反三

 1 import cv2 as cv
 2 
 3 import numpy as np
 4 
 5 # Read image
 6 
 7 img = cv.imread("../bird.png").astype(np.float32)
 8 
 9 H, W, C = img.shape
10 
11 mi = np.mean(img)
12 
13 # Read templete image
14 
15 temp = cv.imread("../bird_e.png").astype(np.float32)
16 
17 Ht, Wt, Ct = temp.shape
18 
19 mt = np.mean(temp)
20 
21 # Templete matching
22 
23 i, j = -1, -1
24 
25 v = -1
26 
27 for y in range(H-Ht):
28 
29     for x in range(W-Wt):
30 
31         _v = np.sum((img[y:y+Ht, x:x+Wt]-mi) * (temp-mt))
32 
33         _v /= (np.sqrt(np.sum((img[y:y+Ht, x:x+Wt]-mi)**2)) * np.sqrt(np.sum((temp-mt)**2)))
34 
35         if _v > v:
36 
37             v = _v
38 
39             i, j = x, y
40 
41 out = img.copy()
42 
43 cv.rectangle(out, pt1=(i, j), pt2=(i+Wt, j+Ht), color=(0,0,255), thickness=1)
44 
45 out = out.astype(np.uint8)
46 
47 # Save result
48 
49 cv.imwrite("out.jpg", out)
50 
51 cv.imshow("result", out)
52 
53 cv.waitKey(0)
54 
55 cv.destroyAllWindows()

 


五. 實驗結果:


ZNCC(零均值歸一化交叉相關)模式匹配結果 ↑
 

六. python實現 S=誤差絕對值之和。不同的 S ,讀者可舉一反三

 1 import cv2
 2 
 3 import numpy as np
 4 
 5 # Read image
 6 
 7 img = cv2.imread("../baby.png").astype(np.float32)
 8 
 9 H, W, C = img.shape
10 
11 # Read templete image
12 
13 temp = cv2.imread("../baby_m.png").astype(np.float32)
14 
15 Ht, Wt, Ct = temp.shape
16 
17 # Templete matching
18 
19 i, j = -1, -1
20 
21 v = 255 * H * W * C
22 
23 for y in range(H-Ht):
24 
25     for x in range(W-Wt):
26 
27         _v = np.sum(np.abs(img[y:y+Ht, x:x+Wt] - temp))
28 
29         if _v < v:
30 
31             v = _v
32 
33             i, j = x, y
34 
35 out = img.copy()
36 
37 # (0,0,255)  代表紅色
38 
39 cv2.rectangle(out, pt1=(i, j), pt2=(i+Wt, j+Ht), color=(0,0,255), thickness=2)
40 
41 out = out.astype(np.uint8)
42 
43 # Save result
44 
45 cv2.imwrite("out.jpg", out)
46 
47 cv2.imshow("result", out)
48 
49 cv2.waitKey(0)
50 
51 cv2.destroyAllWindows()

 


七. 實驗結果:


SAD(誤差絕對值之和)模式匹配結果 ↑
 

八. 寫在最后的話:

    感謝您的閱讀,如果您覺得本文不錯,可以點贊哦!


九. 版權聲明:

    未經作者允許,請勿隨意轉載抄襲,抄襲情節嚴重者,作者將考慮追究其法律責任,創作不易,感謝您的理解和配合!


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM