What are Feature Matching in cV?
Feature Matching takes the descriptor of 1 feature as the initial set is matched with all alternative options in second set mistreatment a long way calculations . therefore, the nearest one is came back for bf go-between , initially we’ve got to form a BF go-between object mistreatment cv.
What is brute force go-between ?
Brute-Force go-between is easy. It takes the descriptor of 1 feature in the initial set and is matched with all alternative options in second set mistreatment a long way calculation. and therefore the nearest one came back.
For BF go-between, initially we’ve got to form the cv.DescriptorMatcher object with BFMatcher as short. It takes 2 ex gratia params. The initial one is NormType. so, It specifies the space measure to be used. By default, it is L2. it’s smart for SIFT, SURF, etc. (L1 is additionally there).
thus, For binary string-based descriptors like ORB, BRIEF, BRISK, etc. hence, Hamming should be used, that uses acting distance as measure. also, If ORB is using WTA_K of three or four, Hamming2 should be used.
Second Param
Second param is a mathematician variable, CrossCheck which is fake by default. If it’s true, go-between returns solely those matches with worth (i,j) such i-th descriptor in set A has j-th descriptor in set B because the best match and vice-versa. That is, the 2 options in each set ought to match one another. so, It provides a consistent result, and could be a smart different to magnitude relation check projected by D.Lowe in SIFT paper.
Once it’s created, 2 vital ways are cv.DescriptorMatcher.match and cv.DescriptorMatcher.knnMatch. the initial one returns the simplest match. Second methodology returns k best matches wherever k is specific by the user. it’s going to be helpful after we ought to do further work on it.
Like we have a tendency to use cv.drawKeypoints to draw keypoints, cv.drawMatches helps North American countries to draw the matches. thus, It stacks 2 pictures horizontally and draws lines from initial image to second image showing best matches.
FLANN primarily based go-between
FLANN stands for quick Library for Approximate Nearest Neighbors. also, It contains a group of algorithms optimized for quick nearest neighbor search in massive datasets and for prime dimensional options. It works quicker than BFMatcher for massive datasets. we are going to see the second example with FLANN primarily based go-between.
For FlannBasedMatcher, it accepts 2 sets of choices that specify the algorithmic program to be used, its connected parameters etc. initial one is Index. For numerous algorithms, the data to be passed is explained in FLANN docs. As a outline, for algorithms like SIFT, SURF etc.
you’ll produce the go-between as follows:
matcher = cv.DescriptorMatcher('FlannBasedMatcher', ...'Index',{ KDTree, Tree,5})
While mistreatment ORB, you’ll pass the subsequent. The commented values are suggested as per the docs, however it did not offer needed ends up in some cases. alternative values worked fine:
matcher = cv.DescriptorMatcher('FlannBasedMatcher', ...'Index',{ LSH,Tablenumber,6,key size,12})
Second possibility is Search. It specifies the quantity of times the trees within the index ought to be recursively traversed. Higher values provide higher exactitude, however additionally takes longer. If you would like to alter the worth, pass:
matcher=cv.DescriptorMatcher('FlannBasedMatcher','Search',{checks,10})
Options
some parameters:-
do_filtering = true;
minHessian = 400;
Images
Prepare a combine of pictures:
im1 = imread(fullfile(mexopencv.root(),'test','box.png'));
im2=imread(fullfile(mexopencv.root(),'test','box_in_scene.png'));
subplot(121), imshow(im1), title('box')
subplot(122), imshow(im2), title('box-in-scene')
Detect
Detect keypoints mistreatment SURF observer
detector=cv.FeatureDetector('SURF','HessianThreshold',minHessian);
keypoints1 = detector.detect(im1);
keypoints2 = detector.detect(im2);
whos keypoints1 keypoints2
disp(key points 1(1))
Name Size Bytes category Attributes
keypoints1 1x786 572592 struct
keypoints2 1x1040 757504 struct
pt: [68.9577 79.3293]
size: 20
angle: 104.5331
response: one.5550e+04
octave: 0
class_id: -1
specify a mask wherever to seem for keypoints
if false
mask = false(size(im2));
mask(100:350,100:350) = true;
keypoints2 = detector.detect(im2, 'Mask',mask);end
Show distribution of keypoint sizes
if ~mexopencv.isOctave()
%HACK: bar graph not enforced in Octave
figure:-
histogram([key points 1.size]), hold on
histogram([keypoints2.size])
xlabel('Keypoint sizes'), ylabel('Count')
legend('keypoints1', 'keypoints2')
hold offend
Filter keypoints by size
if do_filtering
keypoints1 = cv.KeyPointsFilter.runByKeypointSize(key points 1, 0, 50);
keypoints2=cv.KeyPointsFilter.runByKeypointSize(keypoints2, 0, 50);
end
Show distribution of keypoint responses
if ~mexopencv.isOctave()
%HACK: bar graph not enforced in Octave
histogram([key points 1.response]), hold on
histogram([keypoints2.response])
xlabel('Keypoint responses'), ylabel('Count')
legend('keypoints1', 'keypoints2')
hold offend
Filter key points by responses
if do_filtering
keypoints1 = cv.KeyPointsFilter.retainBest(key points 1, 500);
keypoints2 = cv.KeyPointsFilter.retainBest(keypoints2, 500);end
Draw filtered keypoints
subplot(121), imshow(cv.drawKeypoints(im1, keypoints1))
subplot(122), imshow(cv.drawKeypoints(im2, keypoints2))
Compute
Calculate descriptors (feature vectors) mistreatment SURF
extractor = cv.DescriptorExtractor('SURF');
descriptors1 = extractor.compute(im1, keypoints1);
descriptors2 = extractor.compute(im2, keypoints2);
whos descriptors1 descriptors2
Name Size Bytes category Attributes
descriptors1 500x64 128000 single
descriptors2 500x64 128000 single
Match
if true to mix and match descriptor vectors with a brute force go-between
matcher = cv.DescriptorMatcher('BFMatcher', 'NormType','L2');
matcher = cv.DescriptorMatcher('BFMatcher', 'CrossCheck',true);
go-between = cv.DescriptorMatcher('BruteForce');
matches = go-between.match(descriptors1, descriptors2);else if true
nothing Brute-Force kNN Matching with magnitude relation check as per Lowe's paper
go-between = cv.DescriptorMatcher('BruteForce');
matches = go-between.knnMatch(descriptors1, descriptors 2, 2);
idx = cellfun(@(m) m(1).distance < zero.75 * m(2).distance, matches);
matches = cellfun(@(m) m(1), matches(idx));else
to mix and match descriptor vectors mistreatment FLANN go-between
go-between = cv.DescriptorMatcher('FlannBased');
matches = go-between.radiusMatch(descriptors1, descriptors 2, 0.22);
matches = [matches];end
whos matches
disp(matches(1))
Name Size Bytes category Attributes
matches 1x500 240256 struct
queryIdx: zero
trainIdx: 438
imgIdx: 0
distance: zero.3544
Show distribution of match distances
if ~mexopencv.isOctave()
%HACK: bar graph not enforced in Octave
figure
histogram([matches.distance])
xlabel('Match distances'), ylabel('Count')end
Filter matches by distance (“good” matches)
if do_filtering
if true
[~,idx] = sort([matches.distance]);
idx = idx(1:min(50,end));
matches = matches(idx);
else
min_dist = min([matches.distance]);
matches = matches([matches.distance] <= max(3*min_dist, 0.22));
end
Draw matches
out = cv.drawMatches(im1, keypoints1, im2, keypoints2, matches);
figure, imshow(out);
Conclusion on Feature Matching
This paper is the first uniform benchmark to evaluate feature matching. however, Feature Matching suggests Analyzing matching in three different aspects, including matching ability, correspondence sufficiency and efficiency. so, In order to measure these different properties , the paper presents two novel evaluation metrics.
however, On the other hand, the proposed benchmark datasets cover a wide range of scenes and can be used to evaluate matching in different types of problems.
written by: Somay Mangla
reviewed by: Umamah
If you are Interested In Machine Learning You Can Check Machine Learning Internship Program
Also Check Other Technical And Non Technical Internship Programs