Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/opencv/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 去除二值阈值图像中带有连接边的小破折号_Python_Opencv_Image Processing - Fatal编程技术网

Python 去除二值阈值图像中带有连接边的小破折号

Python 去除二值阈值图像中带有连接边的小破折号,python,opencv,image-processing,Python,Opencv,Image Processing,我有一个二进制阈值图像,我想删除图像中的小破折号。它与圆相连。我的主要关注点是提取圆的圆弧 原始图像: 将图像输出为: 我想从图像中删除小破折号 我们删除了小破折号,但也会丢失一些功能。我们需要: 将图像转换为HSV颜色空间 得到 形象 面具 二进制掩码 我们需要确定范围的下限和上限 如我们所见,虚线被删除,但圆变成了点 放大面具 点是可见的,但仍缺少一些特征 反转遮罩 代码: #加载库 进口cv2 将numpy作为np导入 #加载图像

我有一个二进制阈值图像,我想删除图像中的小破折号。它与圆相连。我的主要关注点是提取圆的圆弧

  • 原始图像:

  • 将图像输出为:

  • 我想从图像中删除小破折号
我们删除了小破折号,但也会丢失一些功能。我们需要:

  • 将图像转换为HSV颜色空间

  • 得到

  • 形象

  • 面具


二进制掩码

  • 我们需要确定范围的下限和上限

  • 如我们所见,虚线被删除,但圆变成了点

放大面具

  • 点是可见的,但仍缺少一些特征

反转遮罩


代码:

#加载库
进口cv2
将numpy作为np导入
#加载图像
img=cv2.imread(“GOETr.png”)
#转乘高速列车
hsv=cv2.CVT颜色(img,cv2.COLOR\U BGR2HSV)
#获取二进制掩码
msk=cv2.inRange(hsv,np.数组([0,0214]),np.数组([179255,217]))
#放大面具
krn=cv2.getStructuringElement(cv2.morp_ELLIPSE,(3,3))
dlt=cv2.扩张(msk,krn,迭代次数=8)
#反面具
res=cv2。按位\u非(dlt)
#显示结果
cv2.imshow(“res”,res)
cv2.等待键(0)

您需要更改参数以获得不同的结果。

由于我们有一个空心形状,因此我采用了惰性方法。这是一种解决问题的平滑方法,相对简单(检查从内部到外部的距离),但由于它是在简单闭合形状的假设下运行的,因此会丢失细节。如果这还不够好,让我知道;有更复杂的方法来做你想做的事情,可以得到更干净的结果

因此,基本步骤如下:首先,使用findContours获得形状的内层和外层(放大直到得到两层,我们不必在这种情况下这样做,因为它已经这样做了)

然后,计算从每个点到另一个轮廓上最近点的距离。从图中你可以很好地了解我们的目的。破折号是相对统一图形的明显异常值。在这里,我手动将截止值设置为10,但我们可以使用平均值和标准偏差自动设置截止值

一旦我们删除了异常点,我们就可以使用轮廓重新绘制形状

导入cv2
将numpy作为np导入
#返回平滑的轮廓
def平滑(轮廓、距离、截止):
平滑_con=[];
对于范围内的(len(dists)):
如果距离[a]<截止点:
光滑的(轮廓[a]);
返回np.asarray(平滑控制);
#获取点阵列的距离列表
def distList(src,其他):
dists=[];
对于src中的点:
点=点[0];#放下多余的括号
_,距离=闭合点(点,其他);
附加区(dist);
返回区;
#返回两点的平方距离
def SquaredList(一,二):
dx=1[0]-2[0];
dy=1[1]-2[1];
返回dx*dx+dy*dy;
#查找最近的点(只需进行线性搜索)
def闭合点(点,arr):
#初始跟踪变量
最近=无;
最佳距离=99999999;
#线性搜索
对于arr中的其他内容:
其他=其他[0];#拆下额外的支架
距离=平方距离(点,其他);
如果距离<最佳距离:
最近的=其他;
最佳距离=距离;
返回最近、最佳距离;
#加载图像
img=cv2.imread(“圆圈_虚线.png”);
#做个面具
灰色=cv2.CVT颜色(img,cv2.COLOR_BGR2GRAY);
掩模=cv2.inRange(灰色,0,100);
#获取轮廓#OpenCV 3.4,如果使用OpenCV 2或4,它将返回(轮廓,#)
_,等高线,u=cv2.找到的轮廓(遮罩,cv2.RETR_树,cv2.CHAIN_近似简单);
印刷品(轮廓)我们有两个,内部和外部,不需要先扩张
#分裂
1=等高线[0];
二=等高线[1];
#获得距离
1_dists=distList(1,2);
二区=区列表(二,一);
#转储值大于10
平滑1=平滑(1,1距离,10);
平滑二=平滑(二,二距离,10);
#绘制新轮廓
空白=np.类零(掩码);
cv2.绘制轮廓(空白,[smooth_one],-1,(255),-1);
cv2.绘制轮廓(空白,[smooth_two],-1,(0),-1);
#展示
cv2.imshow(“图像”,img);
cv2.imshow(“平滑”,空白);
cv2.waitKey(0);

也许拨号和腐蚀会有所帮助,看看这个:从udacityI开始,我尝试过形态学转换,但是圆线和虚线的宽度是相同的,所以腐蚀和膨胀是没有用的。正如我在问题
中提到的,我的主要重点是提取圆的一条弧。
用你的解决方案,我认为我们无法提取圆的弧。而且我认为,在提取弧时不会丢失特征。您无法区分虚线和圆弧。无像素差异,无伪影。你的乐观也许令人印象深刻:找到圆圈的中心。然后转换为极坐标,使散列线垂直,圆水平(反之亦然)。然后使用1D形态学删除散列线。然后转换回笛卡尔坐标。@fmw42谢谢您,先生,感谢您的宝贵意见。非常感谢。这种方法适合我。如果我们没有一个清晰的闭合形状,我仍然对其他方法感到好奇。简单的方法,很好的结果+1.