我有两个从cv2.findContours()
接收到的等值线(cont1
和cont2
)。我如何知道它们是否相交?我不需要坐标,我只需要一个布尔值True
或False
。
我尝试了不同的方法,并已尝试与
if ((cont1 & cont2).area() > 0):
...但得到数组没有方法“Area()”的错误
...
cont1array = cv2.findContours(binary1, cv2.RETR_LIST, cv2.CHAIN_APPROX_SIMPLE)[0]
cont2array = cv2.findContours(binary2, cv2.RETR_LIST, cv2.CHAIN_APPROX_SIMPLE)[0]
...
for cont1 in cont1array:
for cont2 in cont2array:
print("cont1")
print(cont1)
print(type(cont1))
print("cont2")
print(cont2)
print(type(cont2))
> if cont1 and cont2 intersect: #i dont know how check intersect
print("yes they intersect")
else:
print("no they do not intersect")
# cont1
# [[172 302]
# [261 301]
# [262 390]
# [173 391]]
# <class 'numpy.ndarray'>
# cont2
# [[ 0 0]
# [ 0 699]
# [499 699]
# [499 0]]
# <class 'numpy.ndarray'>
4条答案
按热度按时间f4t66c6m1#
nathancy给出的答案是可行的,但是在性能方面受到了影响,例如创建3个图像副本来绘制轮廓,在执行时间方面表现迟缓。
我的另一种回答如下:
编辑!!
测试完这段代码后,意识到当轮廓线上没有两个相似点时,这种检查会失败。因此,我重写了检查两条轮廓线相交的算法。
wkyowqbh2#
一旦得到
cv2.findContours()
的两个轮廓,就可以使用AND
的位运算来检测交点。我们可以使用np.logical_and()
,其思想是为每个轮廓创建两个单独的图像,然后对它们使用逻辑AND
操作。(1
或True
)将是交点,因此,由于您只需要获取是否存在交点的布尔值,我们可以检查相交图像,看看是否存在单个正值。如果整个阵列是False
,则轮廓线之间没有相交,但是如果存在单个True
,则轮廓线接触并因此相交。原始图像
检测轮廓
我们现在将两个检测到的轮廓传递给函数并获得这个交集数组:
我们检查
intersection
数组,看看True
是否存在,在等值线相交的地方得到True
或1
,在等值线不相交的地方得到False
或0
。因此我们得到
假
完整代码
bxgwgixi3#
@Ivans和@nathancys的答案是我在这里看到的最好的答案。然而,画线仍然是计算密集型的,特别是当你的轮廓中有很多点的时候,而直接计算位与会损害性能,特别是当你的画布很大的时候。提高性能的一个简单方法是首先检查bbox的交集;如果你看到bbox不相交,你就知道轮廓线不相交。如果你的bbox相交,只要为两个轮廓线绘制最小的填充(或轮廓)ROI,然后计算一个简单的逐位与。我发现这与这里列出的其他技术相比提供了显著的加速比,并防止了在大画布上处理大而复杂的轮廓线的问题。我使用torch来计算bbox ious,以实现简单/清晰。
njthzxwz4#
为了处理一个轮廓包含另一个轮廓的情况,我们可以替换
Nathancy的回答