Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitd750d43

Browse files
authored
Merge pull request#27432 from dkurt:d.kurtaev/ipp_distTransform
Correct IPP distanceTransform results with single thread#27432### Pull Request Readiness Checklistresolves#24082See details athttps://github.com/opencv/opencv/wiki/How_to_contribute#making-a-good-pull-request- [x] I agree to contribute to the project under Apache 2 License.- [x] To the best of my knowledge, the proposed patch is not based on a code under GPL or another license that is incompatible with OpenCV- [x] The PR is proposed to the proper branch- [x] There is a reference to the original bug report and related work- [x] There is accuracy test, performance test and test data in opencv_extra repository, if applicable Patch to opencv_extra has the same branch name.- [x] The feature is well documented and sample code can be built with the project CMake
1 parentb395a2e commitd750d43

File tree

2 files changed

+49
-0
lines changed

2 files changed

+49
-0
lines changed

‎modules/imgproc/src/distransform.cpp‎

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -796,6 +796,22 @@ void cv::distanceTransform( InputArray _src, OutputArray _dst, OutputArray _labe
796796
ippFree( pBuffer );
797797
if (status>=0)
798798
{
799+
// https://github.com/opencv/opencv/issues/24082
800+
// There is probably a rounding issue that leads to non-deterministic behavior
801+
// between runs on positions closer to zeros by x-axis in straight direction.
802+
// As a workaround, we detect the distances that expected to be exact
803+
// number of pixels and round manually.
804+
staticconstfloat correctionDiff =1.0f / (1 <<11);
805+
for (int i =0; i < dst.rows; ++i)
806+
{
807+
float* row = dst.ptr<float>(i);
808+
for (int j =0; j < dst.cols; ++j)
809+
{
810+
float rounded =static_cast<float>(cvRound(row[j]));
811+
if (fabs(row[j] - rounded) <= correctionDiff)
812+
row[j] = rounded;
813+
}
814+
}
799815
CV_IMPL_ADD(CV_IMPL_IPP);
800816
return;
801817
}

‎modules/imgproc/test/test_distancetransform.cpp‎

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -416,4 +416,37 @@ TEST(Imgproc_DistanceTransform, precise_long_dist)
416416
EXPECT_EQ(cv::norm(expected, dist, NORM_INF),0);
417417
}
418418

419+
TEST(Imgproc_DistanceTransform, ipp_deterministic_corner)
420+
{
421+
setNumThreads(1);
422+
423+
Matsrc(1,4096, CV_8U,Scalar(255)), dist;
424+
src.at<uint8_t>(0,0) =0;
425+
distanceTransform(src, dist, DIST_L2, DIST_MASK_PRECISE);
426+
for (int i =0; i < src.cols; ++i)
427+
{
428+
float expected =static_cast<float>(i);
429+
ASSERT_EQ(expected, dist.at<float>(0, i)) <<cv::format("diff: %e", expected - dist.at<float>(0, i));
430+
}
431+
}
432+
433+
TEST(Imgproc_DistanceTransform, ipp_deterministic)
434+
{
435+
setNumThreads(1);
436+
RNG& rng =TS::ptr()->get_rng();
437+
Matsrc(1,800, CV_8U,Scalar(255)), dist;
438+
int p1 =cvtest::randInt(rng) % src.cols;
439+
int p2 =cvtest::randInt(rng) % src.cols;
440+
int p3 =cvtest::randInt(rng) % src.cols;
441+
src.at<uint8_t>(0, p1) =0;
442+
src.at<uint8_t>(0, p2) =0;
443+
src.at<uint8_t>(0, p3) =0;
444+
distanceTransform(src, dist, DIST_L2, DIST_MASK_PRECISE);
445+
for (int i =0; i < src.cols; ++i)
446+
{
447+
float expected =static_cast<float>(min(min(abs(i - p1),abs(i - p2)),abs(i - p3)));
448+
ASSERT_EQ(expected, dist.at<float>(0, i)) <<cv::format("diff: %e", expected - dist.at<float>(0, i));
449+
}
450+
}
451+
419452
}}// namespace

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp