From 1196eb33fcbdc87241d426ccd428718fc81affe9 Mon Sep 17 00:00:00 2001 From: root Date: Fri, 26 Oct 2018 20:25:24 +0000 Subject: [PATCH 1/2] remove non-ideal pairs when using crosscheck in batchdistance --- modules/core/src/batch_distance.cpp | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/modules/core/src/batch_distance.cpp b/modules/core/src/batch_distance.cpp index 71d0e9e3ff..1ce2edb769 100644 --- a/modules/core/src/batch_distance.cpp +++ b/modules/core/src/batch_distance.cpp @@ -297,19 +297,21 @@ void cv::batchDistance( InputArray _src1, InputArray _src2, nidx = Scalar::all(-1); } + if( crosscheck ) { CV_Assert( K == 1 && update == 0 && mask.empty() ); CV_Assert(!nidx.empty()); - Mat tdist, tidx; + Mat tdist, tidx, sdist, sidx; batchDistance(src2, src1, tdist, dtype, tidx, normType, K, mask, 0, false); + batchDistance(src1, src2, sdist, dtype, sidx, normType, K, mask, 0, false); // if an idx-th element from src1 appeared to be the nearest to i-th element of src2, // we update the minimum mutual distance between idx-th element of src1 and the whole src2 set. // As a result, if nidx[idx] = i*, it means that idx-th element of src1 is the nearest // to i*-th element of src2 and i*-th element of src2 is the closest to idx-th element of src1. // If nidx[idx] = -1, it means that there is no such ideal couple for it in src2. - // This O(N) procedure is called cross-check and it helps to eliminate some false matches. + // This O(2N) procedure is called cross-check and it helps to eliminate some false matches. if( dtype == CV_32S ) { for( int i = 0; i < tdist.rows; i++ ) @@ -336,6 +338,13 @@ void cv::batchDistance( InputArray _src1, InputArray _src2, } } } + for( int i = 0; i < sdist.rows; i++ ) + { + if( tidx.at(sidx.at(i)) != i ) + { + nidx.at(i) = -1; + } + } return; } From a68835f7f17401fd43ddd7e77e2b1731a7fafcb9 Mon Sep 17 00:00:00 2001 From: Alexander Alekhin Date: Fri, 16 Nov 2018 19:22:43 +0000 Subject: [PATCH 2/2] features2d(test): add crossCheck=true test --- .../test/test_matchers_algorithmic.cpp | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/modules/features2d/test/test_matchers_algorithmic.cpp b/modules/features2d/test/test_matchers_algorithmic.cpp index 96921518c4..a7116e9bc3 100644 --- a/modules/features2d/test/test_matchers_algorithmic.cpp +++ b/modules/features2d/test/test_matchers_algorithmic.cpp @@ -558,4 +558,23 @@ TEST( Features2d_DMatch, read_write ) ASSERT_NE( strstr(str.c_str(), "4.5"), (char*)0 ); } + +TEST(Features2d_DMatch, issue_11855) +{ + Mat sources = (Mat_(2, 3) << 1, 1, 0, + 1, 1, 1); + Mat targets = (Mat_(2, 3) << 1, 1, 1, + 0, 0, 0); + + Ptr bf = BFMatcher::create(NORM_HAMMING, true); + vector > match; + bf->knnMatch(sources, targets, match, 1, noArray(), true); + + ASSERT_EQ((size_t)1, match.size()); + ASSERT_EQ((size_t)1, match[0].size()); + EXPECT_EQ(1, match[0][0].queryIdx); + EXPECT_EQ(0, match[0][0].trainIdx); + EXPECT_EQ(0.0f, match[0][0].distance); +} + }} // namespace