From 2e9345570f3f5b81b6ebc095a0a9803f57f24c3c Mon Sep 17 00:00:00 2001 From: Scorpion1234567 <1971208858@qq.com> Date: Thu, 20 Mar 2025 22:46:18 +0800 Subject: [PATCH] Merge pull request #27108 from Scorpion1234567:Multithreading-wrapPolar When WARP_INVERSE_MAP is used, accelerate the calculation with multi-threading #27108 ### Pull Request Readiness Checklist See details at https://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 - [ ] The PR is proposed to the proper branch - [ ] There is a reference to the original bug report and related work - [ ] There is accuracy test, performance test and test data in opencv_extra repository, if applicable Patch to opencv_extra has the same branch name. - [ ] The feature is well documented and sample code can be built with the project CMake --- modules/imgproc/src/imgwarp.cpp | 47 ++++++++++++++++++--------------- 1 file changed, 26 insertions(+), 21 deletions(-) diff --git a/modules/imgproc/src/imgwarp.cpp b/modules/imgproc/src/imgwarp.cpp index d512bbf887..38f61333cf 100644 --- a/modules/imgproc/src/imgwarp.cpp +++ b/modules/imgproc/src/imgwarp.cpp @@ -3737,7 +3737,6 @@ void cv::warpPolar(InputArray _src, OutputArray _dst, Size dsize, else Kmag = maxRadius / ssize.width; - int x, y; Mat bufx, bufy, bufp, bufa; bufx = Mat(1, dsize.width, CV_32F); @@ -3745,33 +3744,39 @@ void cv::warpPolar(InputArray _src, OutputArray _dst, Size dsize, bufp = Mat(1, dsize.width, CV_32F); bufa = Mat(1, dsize.width, CV_32F); - for (x = 0; x < dsize.width; x++) + for (int x = 0; x < dsize.width; x++) bufx.at(0, x) = (float)x - center.x; - for (y = 0; y < dsize.height; y++) - { - float* mx = (float*)(mapx.data + y*mapx.step); - float* my = (float*)(mapy.data + y*mapy.step); + cv::parallel_for_(cv::Range(0, dsize.height), [&](const cv::Range& range) { + for (int y = range.start; y < range.end; ++y) { + Mat local_bufx = bufx.clone(); + Mat local_bufy = Mat(1, dsize.width, CV_32F); + Mat local_bufp = Mat(1, dsize.width, CV_32F); + Mat local_bufa = Mat(1, dsize.width, CV_32F); - for (x = 0; x < dsize.width; x++) - bufy.at(0, x) = (float)y - center.y; + for (int x = 0; x < dsize.width; x++) { + local_bufy.at(0, x) = static_cast(y) - center.y; + } - cartToPolar(bufx, bufy, bufp, bufa, 0); + cartToPolar(local_bufx, local_bufy, local_bufp, local_bufa, false); - if (semiLog) - { - bufp += 1.f; - log(bufp, bufp); + if (semiLog) { + local_bufp += 1.f; + log(local_bufp, local_bufp); + } + + float* mx = (float*)(mapx.data + y * mapx.step); + float* my = (float*)(mapy.data + y * mapy.step); + + for (int x = 0; x < dsize.width; x++) { + double rho = local_bufp.at(0, x) / Kmag; + double phi = local_bufa.at(0, x) / Kangle; + mx[x] = static_cast(rho); + my[x] = static_cast(phi) + ANGLE_BORDER; + } } + }); - for (x = 0; x < dsize.width; x++) - { - double rho = bufp.at(0, x) / Kmag; - double phi = bufa.at(0, x) / Kangle; - mx[x] = (float)rho; - my[x] = (float)phi + ANGLE_BORDER; - } - } remap(src, _dst, mapx, mapy, flags & cv::INTER_MAX, (flags & cv::WARP_FILL_OUTLIERS) ? cv::BORDER_CONSTANT : cv::BORDER_TRANSPARENT); }