Python에서 OpenCV를 사용하는 SIFT

Manav Narula 2023년10월10일
  1. 특징 추출을 위한 SIFT 알고리즘
  2. SIFT 클래스를 사용하여 Python에서 OpenCV를 사용하여 SIFT 구현
  3. Python에서 OpenCV를 사용하여 SIFT 알고리즘을 구현하여 두 이미지 일치
  4. 결론
Python에서 OpenCV를 사용하는 SIFT

특징 추출은 이미지 처리 및 기계 학습의 통합 프로세스입니다. 가치있는 정보를 추출하여 원시 데이터를 정보로 변환하는 것을 말합니다.

이미지 처리에서 유효한 키 포인트와 설명자를 찾습니다.

Python에서는 OpenCV 라이브러리를 사용하여 이미지를 처리하고 운영합니다. 이 라이브러리를 사용하여 다양한 기술과 미리 정의된 알고리즘을 적용할 수 있습니다.

이 튜토리얼은 OpenCV를 사용하여 SIFT 알고리즘을 구현하고 Python에서 기능 일치에 사용하는 방법을 보여줍니다. 또한 Python에서 OpenCV를 사용하여 SIFT 알고리즘을 사용하여 두 이미지를 일치시키는 방법을 배웁니다.

특징 추출을 위한 SIFT 알고리즘

SIFT(Scale Invariant Feature Transform)는 복잡하고 유용한 특징 추출 기술입니다. 그것은 회전 변형 또는 스케일 변형일 수 있는 다른 알고리즘의 문제를 극복합니다. 즉, 이미지가 회전되거나 다른 크기로 스케일링되면 추출된 정보가 달라질 수 있습니다.

SIFT 알고리즘은 유효한 키 포인트와 설명자를 추출하여 이 모든 것을 방지합니다. 스케일 및 회전 불변입니다.

우리는 이미 특징 추출에 대해 논의했습니다. 이제 특징 추출을 위한 SIFT 알고리즘과 관련된 단계에 대해 논의하겠습니다.

총 5개의 스테이지가 있습니다.

스케일 공간 극값 감지

첫 번째 단계는 Scale-space Extrema Detection이라고 합니다.

논의한 바와 같이 모든 척도에 존재하는 기능이 필요합니다. 더 큰 규모의 경우 더 큰 창이 필요합니다.

이 단계에서는 다른 스케일링 매개변수를 사용하고 가우시안의 차이, 즉 다양한 스케일링 매개변수 값으로 가우시안 블러링의 차이를 계산합니다. 주어진 스케일링 값을 사용하여 좌표를 선택하고 더 높거나 낮은 스케일링 값이 있는지 확인합니다.

키포인트 현지화

이제 두 번째 단계인 Keypoint Localization으로 넘어가겠습니다. 이 단계는 선택한 핵심 포인트를 걸러냅니다.

Taylor Series 스케일 확장을 사용하여 보다 세련된 핵심 포인트를 얻고 강도를 찾습니다. 강도가 지정된 임계값보다 낮으면 거부됩니다.

오리엔테이션 배정

다음 단계는 오리엔테이션 할당입니다. 논의한 바와 같이 핵심 포인트는 회전 불변이며 이 단계는 동일한 것을 보장합니다.

그래디언트와 그 방향을 계산하기 위해 키 포인트의 주변 영역을 사용합니다. 36개의 빈이 생성되고 히스토그램에 표시되어 360도를 나타내며 80%보다 높은 피크는 새로운 키 포인트로 간주되어 선택한 키 포인트의 방향을 결정하는 데 사용됩니다.

키포인트 설명자

네 번째 단계는 키포인트에 인접한 16x16 블록을 가져와 4x4의 16개 블록으로 나누어 키포인트 디스크립터를 만드는 것을 목표로 합니다. 8개의 빈을 포함하는 각 블록에 대해 방향 히스토그램이 구성됩니다.

이러한 모든 값은 키포인트 설명자 벡터로 표시됩니다.

키포인트 매칭

마지막 단계에는 키포인트 매칭이 포함됩니다. 이웃을 찾아 두 개의 핵심 포인트를 일치시킵니다.

잘못된 일치를 제거하는 데 사용됩니다.

이제 SIFT 알고리즘에 대해 자세히 논의했습니다. Python의 OpenCV 라이브러리를 사용하여 이를 구현하는 방법을 살펴보겠습니다.

SIFT 클래스를 사용하여 Python에서 OpenCV를 사용하여 SIFT 구현

SIFT_create() 생성자 객체를 사용하여 이미지에서 핵심 포인트를 감지할 수 있는 SIFT 클래스의 객체를 생성할 수 있습니다.

모든 매개변수에는 기본값이 있지만 다른 매개변수를 지정할 수 있습니다. 매개변수는 nfeatures, nOctaveLayers, contrastThreshold, edgeThreshold, sigmadescriptorType입니다.

nfeatures 매개변수는 결과에서 선택할 최상의 기능 수를 지정할 수 있습니다. 각 옥타브의 레이어는 nOctaveLayers 매개변수(기본값 3)를 사용하여 지정할 수 있습니다.

contrastThresholdedgeThreshold 값은 약하고 가장자리와 같은 기능을 필터링합니다. 가우시안의 시그마는 소프트 렌즈로 클릭한 사진에 대해 낮출 수 있는 시그마 매개변수를 사용하여 지정됩니다.

마지막 매개변수는 CV_32F 또는 CV_8U일 수 있는 디스크립터 유형을 지정합니다.

이 방법을 사용하는 방법을 살펴보겠습니다.

import numpy as np
import cv2 as cv

i = cv.imread("obj.png")
g = cv.cvtColor(i, cv.COLOR_BGR2GRAY)

sift_ob = cv.SIFT_create()
kp = sift_ob.detect(g, None)
img = cv.drawKeypoints(g, kp, i)

cv.imshow("Output", img)
cv.waitKey(0)
cv.destroyAllWindows()

출력:

OpenCV Python에서 SIFT를 사용하여 키포인트 감지 및 그리기

위의 예를 이해하려고 노력합시다.

imread() 함수를 사용하여 이미지를 읽습니다. 그런 다음 이미지의 색 공간을 변경할 수 있는 cvtColor 방법을 사용하여 이 이미지를 회색조로 변환했습니다.

이 알고리즘은 그레이스케일 이미지에서 잘 작동합니다.

기본값으로 SIFT_create() 함수를 사용하여 객체를 생성했습니다. 주어진 이미지에서 포인트를 식별하기 위해 생성된 객체와 함께 detect() 함수를 사용합니다. 결과를 저장하는 튜플을 반환합니다.

drawKeypoints() 기능을 사용하여 더 나은 시각적 표현을 위해 이미지에 키 포인트를 그립니다. 이 함수에서 튜플과 이미지를 전달합니다.

최종 이미지는 imshow() 함수를 사용하여 표시됩니다.

The waitKey() 기능은 사용자가 어떤 키를 누르기를 기다리면서 출력 창이 자동으로 닫히는 것을 방지했습니다. destroyAllWindows() 함수를 사용하여 창을 닫았습니다.

SIFT는 이전에 OpenCV Contrib 라이브러리에 존재했으며 2020년 특허가 만료되면서 OpenCV에 추가되었습니다. OpenCV 버전 3.4.2.16에서는 더 이상 사용할 수 없습니다.

이제 Python에서 OpenCV를 사용하여 SIFT 알고리즘을 구현하여 두 이미지를 일치시키는 방법에 대해 논의하겠습니다.

Python에서 OpenCV를 사용하여 SIFT 알고리즘을 구현하여 두 이미지 일치

위에서 논의한 것처럼 SIFT 알고리즘을 사용하여 다양한 키 포인트와 디스크립터를 감지할 수 있습니다. 이를 위해 Brute-Force 매처를 사용할 수 있습니다.

Brute-Force 매처는 한 번에 하나의 키포인트와 해당 설명자를 가져와서 다른 이미지의 기능 집합과 일치시키려고 시도하여 가장 가까운 일치 항목을 반환합니다.

따라서 BFMatcher() 생성자를 사용하여 Brute-Force 매처 객체를 생성합니다. 이 개체는 두 개의 매개 변수를 허용합니다.

첫 번째 매개변수는 사용된 거리인 normType 매개변수입니다. 문자열 기반의 경우 NORM_HAMMING을 사용해야 하지만 우리의 경우(SIFT)에는 NORM_L1 또는 NORM_l2를 사용할 수 있습니다.

두 번째 매개변수는 crossCheck이며, True로 설정하면 두 세트 중 해당하는 일치 항목만 반환합니다. BFMatcher 개체를 생성한 후 match() 함수를 사용하여 일치를 위해 두 세트의 디스크립터를 전달할 수 있습니다.

그런 다음 drawMatches() 함수를 사용하여 두 이미지에 각각의 일치 항목을 그릴 수 있습니다. 이미지를 나란히 놓고 일치하는 키포인트를 선으로 연결합니다.

모든 선에는 기능을 식별하는 고유한 색상이 있습니다. 이것의 예를 보자.

Qutub Minar의 다음 두 이미지의 기능을 일치시킵니다.

이미지 1:

일치할 이미지 1

이미지 2:

일치할 이미지 2

암호:

import cv2
import matplotlib.pyplot as plt

# %matplotlib inline

i1 = cv2.imread("q3.jpeg")
i2 = cv2.imread("q4.jpeg")

img1 = cv2.cvtColor(i1, cv2.COLOR_BGR2GRAY)
img2 = cv2.cvtColor(i2, cv2.COLOR_BGR2GRAY)

sift = cv2.SIFT_create()

k_1, des_1 = sift.detectAndCompute(img1, None)
k_2, des_2 = sift.detectAndCompute(img2, None)

bf = cv2.BFMatcher(cv2.NORM_L1, crossCheck=True)

matches = bf.match(des_1, des_2)
matches = sorted(matches, key=lambda x: x.distance)

img3 = cv2.drawMatches(img1, k_1, img2, k_2, matches[:50], img2, flags=2)
cv2.imshow("Output", img3)
cv2.waitKey(0)
cv2.destroyAllWindows()

출력:

Python OpenCV에서 SIFT를 사용한 이미지 특징 매칭

위의 예에서는 SIFT 알고리즘과 Brute-Force 매처를 사용하여 두 이미지의 특징을 일치시켰습니다.

먼저 SIFT 알고리즘을 사용하여 두 이미지의 특징을 추출했습니다. 그런 다음 Brute-Force 매처 개체를 사용하여 이러한 기능을 일치시켰습니다.

drawMatches() 기능을 사용하여 두 이미지에 결과 일치 항목을 그렸습니다.

결론

이 튜토리얼에서는 Python에서 OpenCV를 사용하여 기능 추출을 위한 SIFT 알고리즘을 구현하는 방법을 보여주었습니다. SIFT 알고리즘의 이론에 대해 자세히 논의하고 다른 기술에 비해 장점을 강조했습니다.

이 알고리즘의 5단계가 자세히 설명되어 있습니다. 이들은 Scale-Space Extrema Detection, Keypoint Localization, Orientation Assignment, Keypoint Descriptor 및 Keypoint Matching이었습니다.

우리는 SIFT_create() 개체를 사용하여 SIFT 클래스의 개체를 생성하여 이 기법을 구현하는 방법에 대해 논의했습니다. 이 클래스에서 detect() 메서드의 사용을 강조 표시하고 drawKeypoints() 기능을 사용하여 키 포인트를 그렸습니다.

또한 Python에서 OpenCV를 사용하여 SIFT 알고리즘을 사용하여 두 이미지를 일치시키는 방법에 대해서도 논의했습니다. 이를 위해 먼저 SIFT 알고리즘을 사용하여 특징을 추출했습니다. 그런 다음 Brute-Force 매처의 개체를 만들었습니다.

디스크립터를 객체의 match() 속성에 전달하여 일치 항목을 찾았습니다. 결과는 drawMatches() 기능을 사용하여 시각적 표현을 제공하기 위해 두 이미지에 그려졌습니다.

작가: Manav Narula
Manav Narula avatar Manav Narula avatar

Manav is a IT Professional who has a lot of experience as a core developer in many live projects. He is an avid learner who enjoys learning new things and sharing his findings whenever possible.

LinkedIn

관련 문장 - Python OpenCV