<h1 style="font-size: 32px; font-weight: bold; border-bottom: 2px solid rgb(204, 204, 204); padding: 0px 4px 0px 0px; text-align: left; margin: 0px 0px 10px;">点到多边形的最短距离</h1><p style="white-space: normal;">本章节内容是博主网上收集的,PDF原文下载地址如下:</p><p style="white-space: normal;"><a href="/api/system/download?file=OpenCV-Python-Tutorial-%E4%B8%AD%E6%96%87%E7%89%88.pdf" target="_blank">OpenCV-Python-Tutorial-中文版.pdf(P116 轮廓的性质)</a></p><p style="white-space: normal;"><a href="/upload/file/OpenCV-Python-Tutorial-%E4%B8%AD%E6%96%87%E7%89%88.pdf" target="_blank" title="PDF在线预览">PDF在线预览</a></p><p style="white-space: normal;"><br/></p><p style="margin-top: 0px; margin-bottom: 10px; white-space: normal; padding: 0px; list-style: none; border: 0px; overflow-wrap: break-word; word-break: break-all; line-height: 1.5em; font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; color: rgb(51, 51, 51); box-sizing: border-box;">当前系列所有demo下载地址:</p><p style="margin-top: 0px; margin-bottom: 10px; white-space: normal; padding: 0px; list-style: none; border: 0px; overflow-wrap: break-word; word-break: break-all; line-height: 1.5em; font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; color: rgb(51, 51, 51); box-sizing: border-box;"><a href="https://github.com/GaoRenBao/OpenCv4-Demo" target="_blank" style="margin: 0px; padding: 0px; list-style: none; border: 0px; color: rgb(0, 102, 0); transition-duration: 0.2s; transition-property: opacity; outline: none; opacity: 0.8;">https://github.com/GaoRenBao/OpenCv4-Demo</a></p><p style="margin-top: 0px; margin-bottom: 10px; text-wrap: wrap; padding: 0px; list-style: none; border: 0px; overflow-wrap: break-word; word-break: break-all; line-height: 1.5em; font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; box-sizing: border-box; color: rgb(51, 51, 51);">不同编程语言对应的OpenCv版本以及<span style="">开发环境</span>信息如下:<span style="font-family: Calibri; font-size: 14px;"> </span></p><table border="1" style="border-right: none; border-bottom: none; border-image: initial; border-left: 1px solid rgb(102, 102, 102); border-top: 1px solid rgb(102, 102, 102);"><tbody><tr class="firstRow"><td width="81" valign="top" style="border-color: windowtext rgb(102, 102, 102) rgb(102, 102, 102) windowtext; border-bottom-width: 1px; border-bottom-style: solid; border-right-width: 1px; border-right-style: solid; padding: 5px;"><p style="text-align: center;"><strong><span style="font-family: 宋体; font-size: 14px;">语言</span></strong></p></td><td width="223" valign="top" style="border-color: windowtext rgb(102, 102, 102) rgb(102, 102, 102) windowtext; border-bottom-width: 1px; border-bottom-style: solid; border-right-width: 1px; border-right-style: solid; padding: 5px;"><p style="text-align: center;"><strong><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">OpenCv</span>版本</span></strong></p></td><td width="242" valign="top" style="border-color: windowtext rgb(102, 102, 102) rgb(102, 102, 102) windowtext; border-bottom-width: 1px; border-bottom-style: solid; border-right-width: 1px; border-right-style: solid; padding: 5px;"><p style="text-align: center;"><strong><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">IDE</span></span></strong></p></td></tr><tr><td width="81" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">C#</span></span></p></td><td width="223" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: Calibri; letter-spacing: 0px;">OpenCvSharp4.4.8.0.20230708</span></p></td><td width="242" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">Visual Studio 2022</span></span></p></td></tr><tr><td width="81" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">C++</span></span></p></td><td width="223" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; letter-spacing: 0px;"><span style="font-family: Calibri;">O</span></span><span style="font-family: Calibri; letter-spacing: 0px;">pen</span><span style="font-family: 宋体; letter-spacing: 0px;"><span style="font-family: Calibri;">C</span></span><span style="font-family: Calibri; letter-spacing: 0px;">v-4.5.5-vc14_vc15</span></p></td><td width="242" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">Visual Studio 2022</span></span></p></td></tr><tr><td width="81" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">Python</span></span></p></td><td width="223" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">OpenCv-Python (4.6.0.66)</span></span></p></td><td width="242" valign="top" style="border-top: none; border-left-color: windowtext; border-bottom: 1px solid rgb(102, 102, 102); border-right: 1px solid rgb(102, 102, 102); padding: 5px;"><p><span style="font-family: 宋体; font-size: 14px;"><span style="font-family: Calibri;">PyCharm Community Edition 2022.1.3</span></span></p></td></tr></tbody></table><p><br/></p><p>当前demo演示了如何求解图像中的一个点到一个对象轮廊的最短距离。如果点在轮廊的外部,返回值为负。如果在轮廊上,返回值为0。如果在轮廊内部,返回值为正。</p><p>下面我们以点(50,50)为例:</p><p>dist=cv2.pointPolygonTest(cnt,(50,50),True)</p><p>此函数的第三个参数是measureDist。如果设置为True,就会计算最短距离。如果是False,只会判断这个点与轮廊之间的位置关系(返回值为+1,-1,0)</p><p style="white-space: normal;"><span style="color: rgb(255, 0, 0);">注意:如果你不需要知道具体距离,建议你将第三个参数为False,这样速度会提2到3倍</span></p><p style="white-space: normal;"><br/></p><p style="text-wrap: wrap;">测试原图:<br/></p><p style="text-wrap: wrap;"><img src="/upload/image/6379848768266423382251150.png" title="lightning.png" alt="lightning.png"/></p><p style="text-wrap: wrap;">测试结果:</p><p style="text-wrap: wrap;"><img src="/upload/image/6379848766922860075744359.jpg" title="QQ截图20220911100733.jpg" alt="QQ截图20220911100733.jpg"/></p><p style="white-space: normal;"><br/></p><p style="white-space: normal;"><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px; color: rgb(51, 51, 51); font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; "><span style="font-size: 16px; font-style: italic; font-weight: bold; color: rgb(51, 153, 204); line-height: 18px;">C#版本运行代码如下:</span></strong></p><pre class="brush:c#;toolbar:false">using OpenCvSharp;
using System;
namespace ConsoleApp
{
internal class Program
{
static void Main(string[] args)
{
Mat srcImage = Cv2.ImRead("../../../images/lightning.png");
Mat img = new Mat();
Cv2.CvtColor(srcImage, img, ColorConversionCodes.BGR2GRAY);
Mat threshold = new Mat();
Cv2.Threshold(img, threshold, 127, 255, ThresholdTypes.Binary);
Point[][] contours = new Point[][] { };
HierarchyIndex[] hierarcy;
Cv2.FindContours(threshold, out contours, out hierarcy, RetrievalModes.Tree, ContourApproximationModes.ApproxSimple, null);
Console.WriteLine($"contours len:{contours.Length}");
Point[] cnt = contours[0];
Point point = new Point(50, 50);
Cv2.Circle(srcImage, point, 5, new Scalar(0, 0, 255), -1);
Cv2.ImShow("srcImage", srcImage);
double dist = Cv2.PointPolygonTest(cnt, point, true);
Console.WriteLine($"距离:{dist}");
Cv2.WaitKey(0);
}
}
}</pre><p style="white-space: normal;"><br/></p><p style="white-space: normal;"><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px; color: rgb(51, 51, 51); font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; "><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;"><span style="font-size: 16px; font-style: italic; font-weight: bold; color: rgb(51, 153, 204); line-height: 18px;">C++<strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;">版本运行代码如下:</strong></span><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;"></strong></strong></strong></p><p style="white-space: normal;"><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px; color: rgb(51, 51, 51); font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; "><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;"><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;"></strong></strong></strong></p><pre class="brush:cpp;toolbar:false;">#include <opencv2/opencv.hpp>
#include <opencv2/cvconfig.h>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <string>
#include <cmath>
#include <iostream>
using namespace cv;
using namespace std;
int main()
{
Mat srcImage =cv::imread("../images/lightning.png");
Mat img;
cv::cvtColor(srcImage, img, COLOR_BGR2GRAY);
Mat threshold;
cv::threshold(img, threshold, 127, 255, THRESH_BINARY); // 把黑白颜色反转
vector<vector<Point>> contours;
vector<Vec4i> hierarcy;
findContours(threshold, contours, hierarcy, RETR_TREE, CHAIN_APPROX_SIMPLE, Point(0, 0));
cout << "contours len:" << contours.size() << endl;
vector<Point> cnt = contours[0];
Point point(50, 50);
cv::circle(srcImage, point, 5, Scalar(0, 0, 255), -1);
cv::imshow("srcImage", srcImage);
double dist =cv::pointPolygonTest(cnt, point, true);
cout << "距离:" << dist << endl;
cv::waitKey(0);
}</pre><p style="white-space: normal;"><br/></p><p style="white-space: normal;"><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px; color: rgb(51, 51, 51); font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Noto Sans CJK SC", "WenQuanYi Micro Hei", Arial, sans-serif; "><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;"><span style="font-size: 16px; font-style: italic; font-weight: bold; color: rgb(51, 153, 204); line-height: 18px;">Python<strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;">版本运行代码如下:</strong></span><strong style="margin: 0px; padding: 0px; list-style: none; border: 0px;"></strong></strong></strong></p><pre class="brush:python;toolbar:false">import cv2
srcImage = cv2.imread('../images/lightning.png')
img = cv2.cvtColor(srcImage, cv2.COLOR_BGR2GRAY)
ret, thresh = cv2.threshold(img, 127, 255, 0)
contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
print('contours len:', len(contours))
cnt = contours[0]
point = (50, 50)
cv2.circle(srcImage, point, 5, (0, 0, 255), -1)
cv2.imshow("srcImage", srcImage)
dist = cv2.pointPolygonTest(cnt, point, True)
print("距离:", dist)
cv2.waitKey(0)
cv2.destroyAllWindows()</pre>
点到多边形的最短距离 本章节内容是博主网上收集的,PDF原文下载地址如下:
OpenCV-Python-Tutorial-中文版.pdf(P116 轮廓的性质)
PDF在线预览
当前系列所有demo下载地址:
https://github.com/GaoRenBao/OpenCv4-Demo
不同编程语言对应的OpenCv版本以及开发环境 信息如下:
语言
OpenCv 版本
IDE
C#
OpenCvSharp4.4.8.0.20230708
Visual Studio 2022
C++
O pen C v-4.5.5-vc14_vc15
Visual Studio 2022
Python
OpenCv-Python (4.6.0.66)
PyCharm Community Edition 2022.1.3
当前demo演示了如何求解图像中的一个点到一个对象轮廊的最短距离。如果点在轮廊的外部,返回值为负。如果在轮廊上,返回值为0。如果在轮廊内部,返回值为正。
下面我们以点(50,50)为例:
dist=cv2.pointPolygonTest(cnt,(50,50),True)
此函数的第三个参数是measureDist。如果设置为True,就会计算最短距离。如果是False,只会判断这个点与轮廊之间的位置关系(返回值为+1,-1,0)
注意:如果你不需要知道具体距离,建议你将第三个参数为False,这样速度会提2到3倍
测试原图:
测试结果:
C#版本运行代码如下:
using OpenCvSharp;
using System;
namespace ConsoleApp
{
internal class Program
{
static void Main(string[] args)
{
Mat srcImage = Cv2.ImRead("../../../images/lightning.png");
Mat img = new Mat();
Cv2.CvtColor(srcImage, img, ColorConversionCodes.BGR2GRAY);
Mat threshold = new Mat();
Cv2.Threshold(img, threshold, 127, 255, ThresholdTypes.Binary);
Point[][] contours = new Point[][] { };
HierarchyIndex[] hierarcy;
Cv2.FindContours(threshold, out contours, out hierarcy, RetrievalModes.Tree, ContourApproximationModes.ApproxSimple, null);
Console.WriteLine($"contours len:{contours.Length}");
Point[] cnt = contours[0];
Point point = new Point(50, 50);
Cv2.Circle(srcImage, point, 5, new Scalar(0, 0, 255), -1);
Cv2.ImShow("srcImage", srcImage);
double dist = Cv2.PointPolygonTest(cnt, point, true);
Console.WriteLine($"距离:{dist}");
Cv2.WaitKey(0);
}
}
}
C++版本运行代码如下:
#include <opencv2/opencv.hpp>
#include <opencv2/cvconfig.h>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <string>
#include <cmath>
#include <iostream>
using namespace cv;
using namespace std;
int main()
{
Mat srcImage =cv::imread("../images/lightning.png");
Mat img;
cv::cvtColor(srcImage, img, COLOR_BGR2GRAY);
Mat threshold;
cv::threshold(img, threshold, 127, 255, THRESH_BINARY); // 把黑白颜色反转
vector<vector<Point>> contours;
vector<Vec4i> hierarcy;
findContours(threshold, contours, hierarcy, RETR_TREE, CHAIN_APPROX_SIMPLE, Point(0, 0));
cout << "contours len:" << contours.size() << endl;
vector<Point> cnt = contours[0];
Point point(50, 50);
cv::circle(srcImage, point, 5, Scalar(0, 0, 255), -1);
cv::imshow("srcImage", srcImage);
double dist =cv::pointPolygonTest(cnt, point, true);
cout << "距离:" << dist << endl;
cv::waitKey(0);
}
Python版本运行代码如下:
import cv2
srcImage = cv2.imread('../images/lightning.png')
img = cv2.cvtColor(srcImage, cv2.COLOR_BGR2GRAY)
ret, thresh = cv2.threshold(img, 127, 255, 0)
contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
print('contours len:', len(contours))
cnt = contours[0]
point = (50, 50)
cv2.circle(srcImage, point, 5, (0, 0, 255), -1)
cv2.imshow("srcImage", srcImage)
dist = cv2.pointPolygonTest(cnt, point, True)
print("距离:", dist)
cv2.waitKey(0)
cv2.destroyAllWindows()