diff --git a/doc/tutorials/imgproc/histograms/histogram_comparison/histogram_comparison.markdown b/doc/tutorials/imgproc/histograms/histogram_comparison/histogram_comparison.markdown index 9fcb0a46f9..2a7517fd95 100644 --- a/doc/tutorials/imgproc/histograms/histogram_comparison/histogram_comparison.markdown +++ b/doc/tutorials/imgproc/histograms/histogram_comparison/histogram_comparison.markdown @@ -25,7 +25,7 @@ Theory - To compare two histograms ( \f$H_{1}\f$ and \f$H_{2}\f$ ), first we have to choose a *metric* (\f$d(H_{1}, H_{2})\f$) to express how well both histograms match. -- OpenCV implements the function @ref cv::compareHist to perform a comparison. It also offers 4 +- OpenCV implements the function @ref cv::compareHist to perform a comparison. It also offers 6 different metrics to compute the matching: -# **Correlation ( cv::HISTCMP_CORREL )** \f[d(H_1,H_2) = \frac{\sum_I (H_1(I) - \bar{H_1}) (H_2(I) - \bar{H_2})}{\sqrt{\sum_I(H_1(I) - \bar{H_1})^2 \sum_I(H_2(I) - \bar{H_2})^2}}\f] @@ -36,12 +36,18 @@ Theory -# **Chi-Square ( cv::HISTCMP_CHISQR )** \f[d(H_1,H_2) = \sum _I \frac{\left(H_1(I)-H_2(I)\right)^2}{H_1(I)}\f] - -# **Intersection ( method=cv::HISTCMP_INTERSECT )** + -# **Intersection ( cv::HISTCMP_INTERSECT )** \f[d(H_1,H_2) = \sum _I \min (H_1(I), H_2(I))\f] -# **Bhattacharyya distance ( cv::HISTCMP_BHATTACHARYYA )** \f[d(H_1,H_2) = \sqrt{1 - \frac{1}{\sqrt{\bar{H_1} \bar{H_2} N^2}} \sum_I \sqrt{H_1(I) \cdot H_2(I)}}\f] + -# **Alternative Chi-Square ( cv::HISTCMP_CHISQR_ALT )** + \f[d(H_1,H_2) = 2 * \sum _I \frac{\left(H_1(I)-H_2(I)\right)^2}{H_1(I)+H_2(I)}\f] + + -# **Kullback-Leibler divergence ( cv::HISTCMP_KL_DIV )** + \f[d(H_1,H_2) = \sum _I H_1(I) \log \left(\frac{H_1(I)}{H_2(I)}\right)\f] */ + Code ---- @@ -123,7 +129,7 @@ Explanation @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Convert to HSV half @end_toggle -- Initialize the arguments to calculate the histograms (bins, ranges and channels H and S ). +- Initialize the arguments to calculate the histograms (bins, ranges and channels H and S). @add_toggle_cpp @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Using 50 bins for hue and 60 for saturation @@ -151,7 +157,7 @@ Explanation @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Calculate the histograms for the HSV images @end_toggle -- Apply sequentially the 4 comparison methods between the histogram of the base image (hist_base) +- Apply sequentially the 6 comparison methods between the histogram of the base image (hist_base) and the other histograms: @add_toggle_cpp @@ -182,15 +188,17 @@ Results are from the same source. For the other two test images, we can observe that they have very different lighting conditions, so the matching should not be very good: --# Here the numeric results we got with OpenCV 3.4.1: - *Method* | Base - Base | Base - Half | Base - Test 1 | Base - Test 2 - ----------------- | ------------ | ------------ | -------------- | --------------- - *Correlation* | 1.000000 | 0.880438 | 0.20457 | 0.0664547 - *Chi-square* | 0.000000 | 4.6834 | 2697.98 | 4763.8 - *Intersection* | 18.8947 | 13.022 | 5.44085 | 2.58173 - *Bhattacharyya* | 0.000000 | 0.237887 | 0.679826 | 0.874173 +-# Here the numeric results we got with OpenCV 4.12.0: + *Method* | Base - Base | Base - Half | Base - Test 1 | Base - Test 2 + ------------------- | ------------ | ------------ | -------------- | --------------- + *Correlation* | 1.000000 | 0.880438 | 0.20457 | 0.065752 + *Chi-square* | 0.000000 | 0.328307 | 181.674 | 80.1494 + *Intersection* | 1.000000 | 0.75005 | 0.315061 | 0.0908022 + *Bhattacharyya* | 0.000000 | 0.237866 | 0.679825 | 0.873709 + *Chi-Square alt.* | 0.000000 | 0.395046 | 2.31572 | 3.41024 + *KL divergence* | 0.000000 | 0.321064 | 2.6616 | 9.55412 + For the *Correlation* and *Intersection* methods, the higher the metric, the more accurate the match. As we can see, the match *base-base* is the highest of all as expected. Also we can observe - that the match *base-half* is the second best match (as we predicted). For the other two metrics, - the less the result, the better the match. We can observe that the matches between the test 1 and - test 2 with respect to the base are worse, which again, was expected. + that the match *base-half* is the second best match (as we predicted). For the other four metrics, + the less the result, the better the match. diff --git a/samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp b/samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp index dcbcf8d568..2e08385577 100644 --- a/samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp +++ b/samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp @@ -66,20 +66,20 @@ int main( int argc, char** argv ) Mat hist_base, hist_half_down, hist_test1, hist_test2; calcHist( &hsv_base, 1, channels, Mat(), hist_base, 2, histSize, ranges, true, false ); - normalize( hist_base, hist_base, 0, 1, NORM_MINMAX, -1, Mat() ); + normalize( hist_base, hist_base, 1, 0, NORM_L1, -1, Mat() ); calcHist( &hsv_half_down, 1, channels, Mat(), hist_half_down, 2, histSize, ranges, true, false ); - normalize( hist_half_down, hist_half_down, 0, 1, NORM_MINMAX, -1, Mat() ); + normalize( hist_half_down, hist_half_down, 1, 0, NORM_L1, -1, Mat() ); calcHist( &hsv_test1, 1, channels, Mat(), hist_test1, 2, histSize, ranges, true, false ); - normalize( hist_test1, hist_test1, 0, 1, NORM_MINMAX, -1, Mat() ); + normalize( hist_test1, hist_test1, 1, 0, NORM_L1, -1, Mat() ); calcHist( &hsv_test2, 1, channels, Mat(), hist_test2, 2, histSize, ranges, true, false ); - normalize( hist_test2, hist_test2, 0, 1, NORM_MINMAX, -1, Mat() ); + normalize( hist_test2, hist_test2, 1, 0, NORM_L1, -1, Mat() ); //! [Calculate the histograms for the HSV images] //! [Apply the histogram comparison methods] - for( int compare_method = 0; compare_method < 4; compare_method++ ) + for( int compare_method = 0; compare_method < 6; compare_method++ ) { double base_base = compareHist( hist_base, hist_base, compare_method ); double base_half = compareHist( hist_base, hist_half_down, compare_method ); diff --git a/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java b/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java index fb65dc6d23..49370fa20b 100644 --- a/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java +++ b/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java @@ -52,23 +52,23 @@ class CompareHist { List hsvBaseList = Arrays.asList(hsvBase); Imgproc.calcHist(hsvBaseList, new MatOfInt(channels), new Mat(), histBase, new MatOfInt(histSize), new MatOfFloat(ranges), false); - Core.normalize(histBase, histBase, 0, 1, Core.NORM_MINMAX); + Core.normalize(histBase, histBase, 1, 0, Core.NORM_L1); List hsvHalfDownList = Arrays.asList(hsvHalfDown); Imgproc.calcHist(hsvHalfDownList, new MatOfInt(channels), new Mat(), histHalfDown, new MatOfInt(histSize), new MatOfFloat(ranges), false); - Core.normalize(histHalfDown, histHalfDown, 0, 1, Core.NORM_MINMAX); + Core.normalize(histHalfDown, histHalfDown, 1, 0, Core.NORM_L1); List hsvTest1List = Arrays.asList(hsvTest1); Imgproc.calcHist(hsvTest1List, new MatOfInt(channels), new Mat(), histTest1, new MatOfInt(histSize), new MatOfFloat(ranges), false); - Core.normalize(histTest1, histTest1, 0, 1, Core.NORM_MINMAX); + Core.normalize(histTest1, histTest1, 1, 0, Core.NORM_L1); List hsvTest2List = Arrays.asList(hsvTest2); Imgproc.calcHist(hsvTest2List, new MatOfInt(channels), new Mat(), histTest2, new MatOfInt(histSize), new MatOfFloat(ranges), false); - Core.normalize(histTest2, histTest2, 0, 1, Core.NORM_MINMAX); + Core.normalize(histTest2, histTest2, 1, 0, Core.NORM_L1); //! [Calculate the histograms for the HSV images] //! [Apply the histogram comparison methods] - for( int compareMethod = 0; compareMethod < 4; compareMethod++ ) { + for( int compareMethod = 0; compareMethod < 6; compareMethod++ ) { double baseBase = Imgproc.compareHist( histBase, histBase, compareMethod ); double baseHalf = Imgproc.compareHist( histBase, histHalfDown, compareMethod ); double baseTest1 = Imgproc.compareHist( histBase, histTest1, compareMethod ); diff --git a/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py b/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py index 08d0dc3564..5a070e09b9 100644 --- a/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py +++ b/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py @@ -45,20 +45,20 @@ channels = [0, 1] ## [Calculate the histograms for the HSV images] hist_base = cv.calcHist([hsv_base], channels, None, histSize, ranges, accumulate=False) -cv.normalize(hist_base, hist_base, alpha=0, beta=1, norm_type=cv.NORM_MINMAX) +cv.normalize(hist_base, hist_base, alpha=1, beta=0, norm_type=cv.NORM_L1) hist_half_down = cv.calcHist([hsv_half_down], channels, None, histSize, ranges, accumulate=False) -cv.normalize(hist_half_down, hist_half_down, alpha=0, beta=1, norm_type=cv.NORM_MINMAX) +cv.normalize(hist_half_down, hist_half_down, alpha=1, beta=0, norm_type=cv.NORM_L1) hist_test1 = cv.calcHist([hsv_test1], channels, None, histSize, ranges, accumulate=False) -cv.normalize(hist_test1, hist_test1, alpha=0, beta=1, norm_type=cv.NORM_MINMAX) +cv.normalize(hist_test1, hist_test1, alpha=1, beta=0, norm_type=cv.NORM_L1) hist_test2 = cv.calcHist([hsv_test2], channels, None, histSize, ranges, accumulate=False) -cv.normalize(hist_test2, hist_test2, alpha=0, beta=1, norm_type=cv.NORM_MINMAX) +cv.normalize(hist_test2, hist_test2, alpha=1, beta=0, norm_type=cv.NORM_L1) ## [Calculate the histograms for the HSV images] ## [Apply the histogram comparison methods] -for compare_method in range(4): +for compare_method in range(6): base_base = cv.compareHist(hist_base, hist_base, compare_method) base_half = cv.compareHist(hist_base, hist_half_down, compare_method) base_test1 = cv.compareHist(hist_base, hist_test1, compare_method)