SIFT is among the most popular feature detection algorithms. Continue reading below to know how to accomplish SIFT feature extraction using OpenCV in Python.
So what are the features in an image? Although there is no exact or universal definition of the features in an image, simply put, the features in an image are the information that defines the image.
Let’s say, we have an image of the book cover of “The Alchemist.”
And if we talk about its features, everything in the image is the features of the image. All the letters, edges, pyramids, objects, space between the letters, blobs, ridges, etc. are the features of the image.
To detect these features from an image we use the feature detection algorithms. There are various feature detection algorithms, such as SIFT, SURF, GLOH, and HOG. For this Python tutorial, we will be using SIFT Feature Extraction Algorithm Using the OpenCV library and extract features of an image.
There are many applications of image feature detection and comparing two images is one of the most important applications.
So here in this Python tutorial, first, we will write Python code to detect or extract features in an image using the Scale Invariant Feature Transform (SIFT) algorithm and OpenCV. Then we will compare the two images based on the extracted features. Before we jump to the Python code, let’s install the dependencies.
Install Python OpenCV Contribution Library
Unfortunately, the OpenCV library does not come with the implementation of SIFT algorithms. Thus, we will be installing the community contribution OpenCV library, which supports all the features provided by the standard OpenCV library and many more.
To install the community contribution version of Python OpenCV, run the following pip command on your terminal or command prompt:
pip install opencv-contrib-python
This command will install the
opencv-contrib-python library for your Python environment. To install numpy, run the following pip command:
pip install numpy
For this tutorial, we will be using the following image “book.jpg.”
We would suggest you save the image file in the same directory of your Python script, so you can easily load the image with a relative path.
Now we are all done with the dependencies. So, let’s open your favorite Python IDE or Text editor and start coding.
How to Perform SIFT Feature Extraction Using OpenCV in Python?
Let’s start with importing the module with the following command:
import cv2 as cv
After importing the module, load the image using the OpenCV
cv.imread()method as shown below:
#load image image = cv.imread("book.jpg")
After loading the image, convert the image into a GrayScale image because we do not want to perform the feature extraction on the default Blue, Green, and Red (BGR) image. Doing so will have no effect on extracting features.
To convert a BGR image to GrayScale, we use the OpenCV
cv.cvtColor()method as shown below:
#convert to grayscale image gray_scale = cv.cvtColor(image, cv.COLOR_BGR2GRAY)
Now, let’s load the SIFT algorithm by initializing its object. To initialize the SIFT object we can use the
#initialize SIFT object sift = cv.xfeatures2d.SIFT_create()
Now with the help of the
sift object, let’s detect all the features in the
image. And this can be performed with the help of sift
#detect keypoints keypoints, _= sift.detectAndCompute(image, None)
Here, we are detecting the
keypoints in the image, and the
None is the attribute value for the
mask. Because here we are finding all the
keypoints and features of the image, that’s why the value of the mask is None. The value of the mask can be provided when we are looking for the keypoints or features for a specific portion.
detectAndCompute(image, None)method returns two values, keypoints and descriptors. For this program, we do not require
descriptors and that’s why we use the underscore
After detecting the features let’s draw all the key points on the
gray_scale image. To draw all the keypoints on an image we can use the
#draw keypoints sift_image = cv.drawKeypoints(gray_scale, keypoints, None)
Now let’s see the sift_image with the
#show image cv.imshow("Features Image", sift_image) #hold the window cv.waitKey(0)
Now put all the code together and execute.
#Python Program to Extract Features from an image using SIFT Feature Extraction
import cv2 as cv #load image image = cv.imread("book.jpg") #convert to grayscale image gray_scale = cv.cvtColor(image, cv.COLOR_BGR2GRAY) #initialize SIFT object sift = cv.xfeatures2d.SIFT_create() #detect keypoints keypoints, _= sift.detectAndCompute(image, None) #draw keypoints sift_image = cv.drawKeypoints(gray_scale, keypoints, None) cv.imshow("Features Image", sift_image) cv.waitKey(0)
When you execute the above program you will see a similar output like this:
From the above image, you can see that the OpenCV SIFT algorithm put all the key points on the image.
Match Two Images in OpenCV Using the SIFT Extraction Feature
Now that you know how to extract features in an image, let’s try something. With the help of the extracted features, we can compare 2 images and look for the common features in them.
Let’s say we have two images of a book. The first image, image1, is the front cover of the book as shown below:
And the second image image2 is the front and back cover of the same book:
Now if we want to compare both the images and look for the common components then we have to first extract features from individual images and compare them.
To extract the features from both the images we will use the SIFT algorithm and match the features with Brute Force Matcher.
Let’s start coding.
First, import the OpenCV module and load both the images:
import cv2 as cv #load images image1 = cv.imread("image1.jpg") image2 = cv.imread("image2.jpg")
Next, convert both the images into GrayScale images:
#convert to grayscale image gray_scale1 = cv.cvtColor(image1, cv.COLOR_BGR2GRAY) gray_scale2 = cv.cvtColor(image2, cv.COLOR_BGR2GRAY)
Initialize the SIFT object and detect
keypoints and descriptors(
des1, des2) from both the images
image2with the help of the
#initialize SIFT object sift = cv.xfeatures2d.SIFT_create() keypoints1, des1= sift.detectAndCompute(image1, None) keypoints2, des2= sift.detectAndCompute(image2, None)
Note: The Descriptors define the features independent of the properties of the image.
As we have Descriptors for both the images, now we can use the Brute Force Matcher to match the descriptors. The Brute Force Matcher will compare the descriptor and match the closest ones.
To use the Brute Force Matcher in OpenCV first we need to initialize its object using the
BFMatcher() class as show below:
# initialize Brute force matching bf = cv.BFMatcher(cv.NORM_L1, crossCheck=True)
Now match the descriptors
des2 with the
matches = bf.match(des1,des2)
bf.match()method matches both the descriptors and returns a list of
matched objects. And each
matched object contains some information, including distance.
The smaller the distance, the better is the match. So, let’s sort all the
matches based on the distance of individual
#sort the matches matches = sorted(matches, key= lambda match : match.distance)
Now we need to draw all the matches with the help of
matched_imge = cv.drawMatches(image1, keypoints1, image2, keypoints2, matches[:30], None)
Here we are only drawing the best 30 matches with the
matches[:30]parameter. Let’s show all the matched images (matched_image) with the
cv.imshow("Matching Images", matched_imge) cv.waitKey(0)
Now put all code together and execute.
#Python program to compare two Images with SIFT Feature Extraction
import cv2 as cv #load images image1 = cv.imread("image1.jpg") image2 = cv.imread("image2.jpg") #convert to grayscale image gray_scale1 = cv.cvtColor(image1, cv.COLOR_BGR2GRAY) gray_scale2 = cv.cvtColor(image2, cv.COLOR_BGR2GRAY) #initialize SIFT object sift = cv.xfeatures2d.SIFT_create() keypoints1, des1= sift.detectAndCompute(image1, None) keypoints2, des2= sift.detectAndCompute(image2, None) # initialize Brute force matching bf = cv.BFMatcher(cv.NORM_L1, crossCheck=True) matches = bf.match(des1,des2) #sort the matches matches = sorted(matches, key= lambda match : match.distance) matched_imge = cv.drawMatches(image1, keypoints1, image2, keypoints2, matches[:30], None) cv.imshow("Matching Images", matched_imge) cv.waitKey(0)
In this Python tutorial, we learned how to detect features in an image using the OpenCV SIFT algorithm. The Standard OpenCV library does not provide SIFT algorithm implementation that’s why here we have used its contribution version, which contains more features than the standard OpenCV module. Here, you also learned how to compare two images using the SIFT algorithm.
People are also reading: