방법

1. 템플릿 매칭방법을 선택하고, 매칭을 시작한다.

2. 방법에따라 최대값을 찾을 것인지, 최소값을 찾을 것인지 정한다.

3. 그 부분에 사각형을 그린다.


코드

#include <opencv2/opencv.hpp>

#include <opencv2/highgui.hpp>


using namespace cv;

using namespace std;

int main()

{

Mat srcImage = imread("image4/alphabet.bmp", CV_LOAD_IMAGE_GRAYSCALE);

if (srcImage.empty())

return -1;


Mat tImage1 = imread("image4/A.bmp", CV_LOAD_IMAGE_GRAYSCALE);

Mat tImage2 = imread("image4/S.bmp", CV_LOAD_IMAGE_GRAYSCALE);

Mat tImage3 = imread("image4/b.bmp", CV_LOAD_IMAGE_GRAYSCALE);

Mat tImage4 = imread("image4/m.bmp", CV_LOAD_IMAGE_GRAYSCALE);


Mat dstImage;

cvtColor(srcImage, dstImage, COLOR_GRAY2BGR);


double minVal, maxVal;

Point minLoc, maxLoc;

Mat result;


// 제곱차 매칭 방법(TM_SQDIFF) 어두운곳이 매칭지점

matchTemplate(srcImage, tImage1, result, TM_SQDIFF);

imshow("TM_SQDIFF", result);

//비교한 MAT중에서 가장 큰 값을 찾는다.

minMaxLoc(result, &minVal, NULL, &minLoc, NULL);

rectangle(dstImage, minLoc,

Point(minLoc.x + tImage1.cols, minLoc.y + tImage1.rows), Scalar(255, 0, 0), 2); //blue


// 정규화된 제곱차 매칭 방법(TM_SQDIFF_NORMED) 어두운곳이 매칭지점

matchTemplate(srcImage, tImage2, result, TM_SQDIFF_NORMED);

imshow("TM_SQDIFF_NORMED", result);

minMaxLoc(result, &minVal, NULL, &minLoc, NULL);

rectangle(dstImage, minLoc,

Point(minLoc.x + tImage2.cols, minLoc.y + tImage2.rows), Scalar(0, 255, 0), 2); //green


// 정규화된 상관관계 방법(TM_CCORR_NORMED) 밝은곳이 매칭지점

matchTemplate(srcImage, tImage3, result, TM_CCORR_NORMED);

imshow("TM_CCORR_NORMED", result);


minMaxLoc(result, NULL, &maxVal, NULL, &maxLoc);

rectangle(dstImage, maxLoc,

Point(maxLoc.x + tImage3.cols, maxLoc.y + tImage3.rows), Scalar(0, 0, 255), 2); //red


// 정규화된 상관계수 방법(TM_CCOEFF_NORMED) 밝은곳이 매칭지점

matchTemplate(srcImage, tImage4, result, TM_CCOEFF_NORMED);

imshow("TM_CCOEFF_NORMED", result);

minMaxLoc(result, NULL, &maxVal, NULL, &maxLoc);

rectangle(dstImage, maxLoc,

Point(maxLoc.x + tImage4.cols, maxLoc.y + tImage4.rows), Scalar(255, 0, 255), 2);//puple


imshow("dstImage", dstImage);

waitKey();

return 0;

}



image안에서 x, y로 한칸씩 이동하면서 템플릿을 겹쳐 놓고 각 셀의 차이나 곱의 합을 계산해서 result배열을 만들어서 돌려 준다. 이때 image의 크기는 템플릿의 크기보다 커야 하고 계산 방식은 method로 정해진다.

  • CV_TM_SQDIFF -- 각 픽셀의 제곱의 차이
R(x,y)= \sum _{x',y'} (T(x',y')-I(x+x',y+y'))^2
  • CV_TM_SQDIFF_NORMED  -- CV_TM_SQDIFF / sqrt(각 픽셀의 제곱의 곱)

R(x,y)= \frac{\sum_{x',y'} (T(x',y')-I(x+x',y+y'))^2}{\sqrt{\sum_{x',y'}T(x',y')^2 \cdot \sum_{x',y'} I(x+x',y+y')^2}}

  • CV_TM_CCORR -- 각 픽셀의 곱의 합 (교차 상관)
R(x,y)= \sum _{x',y'} (T(x',y')  \cdot I(x+x',y+y'))
  • CV_TM_CCORR_NORMED -- CV_TM_CCORR / sqrt(각 픽셀의 제곱의 곱)
R(x,y)= \frac{\sum_{x',y'} (T(x',y') \cdot I(x+x',y+y'))}{\sqrt{\sum_{x',y'}T(x',y')^2 \cdot \sum_{x',y'} I(x+x',y+y')^2}}


  • CV_TM_CCOEFF -- 상관계수
R(x,y)= \sum _{x',y'} (T'(x',y')  \cdot I(x+x',y+y'))
  • CV_TM_CCOEFF_NORMED -- CV_TM_CCOEFF / sqrt(각 픽셀의 제곱의 곱)
NCC- 빠른 정상화 간 상관관계

R(x,y)= \frac{ \sum_{x',y'} (T'(x',y') \cdot I'(x+x',y+y')) }{ \sqrt{\sum_{x',y'}T'(x',y')^2 \cdot \sum_{x',y'} I'(x+x',y+y')^2} }


구현 결과



'Programming > openCV' 카테고리의 다른 글

13. Hough Circles  (0) 2017.04.04
iterator의 개념  (0) 2017.04.04
11. Emboss, sketch, 수채화  (0) 2017.04.04
10. 마우스로 영역을 지정한 부분만 엣지 검출  (0) 2017.04.04
9. sobel Filter / Canny Edge  (0) 2017.04.04

+ Recent posts