cv::findContours 返回的轮廓是否具有一致的方向?

Do contours returned by cv::findContours have a consistent orientation?

我正在使用 OpenCV 的 cv::findContours 函数来提取二值图像中的轮廓,特别是,我正在提取轮廓的层次结构(使用 CV_RETR_CCOMP 标志)。在我进一步处理这些轮廓的某些时候,我需要依赖这些轮廓的 一致的顶点方向(即逆时针与顺时针).

当然,我可以使用等高线面积的符号(由 cv::contourArea(..., true) 计算)自己确定方向,但我想知道这是否有必要(除此之外,它甚至不起作用对于面积为 0 的轮廓,即源图像中的细线)或者如果 cv::findContours 已经保证生成的轮廓的方向一致。我确实检查了一些生成的轮廓,cv::contourArea 确实 看起来 到 return 外部轮廓的负值和内部轮廓的正值。但是,我在 OpenCV 文档中找不到任何实际的保证

那么,是否特别保证cv::findContours编辑的轮廓return始终具有一致的方向? 这在任何地方都有记录吗?或者它是否因版本而异(我的版本是 2.4.5)?实际的 paper on the algorithm referenced in the documentation 是否已经对此有所说明?或者也许对 OpenCV 的实际实现有更多了解的人可以比接口文档多说一点?

我相信 Appendix I 的步骤 14(在您引用的 [Suzuki85] 论文“通过边界跟踪对数字化二进制图像进行拓扑结构分析”)根据以下内容涵盖您的问题:

(1) Select 以下之一:
(a) 若f i, j = 1且f i, j - 1 = 0,则判定像素点( i, j )是跟随外边界起点的边界,递增NBD,并且( i 1, j 1 ) + ( i, j - 1 ).
(b) ...

(2) 取决于新发现的边框类型和...

(3) 从起点( i, j ),沿着检测到的边界...

(4) 若f i, j != 1,则LNBD = | f i, j |并从像素 ( i, j + 1 ) 恢复光栅扫描。当扫描到达图片的右下角时,算法终止。

cv:findContours 返回的轮廓应该具有一致的方向。外轮廓应逆时针方向,内轮廓顺时针方向。这直接来自 Suzuki's and Abe's paper.

的附录 1 中描述的算法

图像从左上到右下逐行扫描。当找到属于边界的像素时,边界之后按逆时针顺序查看第一个像素的邻居(参见算法中的步骤 3.3),直到找到非背景像素。这将添加到轮廓中,并从该像素继续搜索。

重要的是,在第一次迭代中,首先查看的邻居取决于它是内边界还是外边界。在外边界的情况下,首先访问右手边的邻居;在内部边界的情况下,它是左手边的邻居。在下一个搜索步骤中,搜索从访问的最后一个像素开始。

由于从左上角到右下角扫描,在检测到外边界时,可以确保边界像素左侧和顶部的所有相邻像素都是背景像素。对于内边界,情况恰恰相反,左侧和顶部的所有邻居都是非背景像素。

结合访问相邻像素的不同起始位置,这会导致轮廓的可预测方向。

此算法在 icvFetchContour function 中实现,由 cv:findContour 内部使用。从那里可以清楚地看出,像素是按照访问顺序添加到轮廓多边形中的。

正如 documentation for cv::findContours 特别指出的那样,他们实现了 Suzuki 等人的算法。正如在本文中明确定义了访问像素的方向和顺序,我认为可以假设方向是有保证的。