背景介绍
测试图如下,图中有个别米粒相互粘连,本文主要演示如何使用opencv用两种不同方法将其分割并计数。
方法一:基于分水岭算法
基于分水岭算法分割步骤如下:
【1】高斯滤波 + 二值化 + 开运算
gray = cv2.cvtcolor(img, cv2.color_bgr2gray)gray = cv2.gaussianblur(gray,(5,5),0)ret, binary= cv2.threshold(gray, 115, 255, cv2.thresh_binary) kernel = np.ones((5, 5), np.uint8)binary = cv2.morphologyex(binary, cv2.morph_open, kernel, iterations=1)cv2.imshow('thres', binary)
【2】距离变换 + 提取前景
dist = cv2.distancetransform(binary, cv2.dist_l2, 3)dist_out = cv2.normalize(dist, 0, 1.0, cv2.norm_minmax)cv2.imshow('distance-transform', dist_out * 100)ret, surface = cv2.threshold(dist_out, 0.35*dist_out.max(), 255, cv2.thresh_binary)cv2.imshow('surface', surface)sure_fg = np.uint8(surface)# 转成8位整型cv2.imshow('sure foreground', sure_fg)
【3】标记位置区域
# 未知区域标记为0markers[unknown == 255] = 0kernel = np.ones((5, 5), np.uint8)binary = cv2.morphologyex(binary, cv2.morph_dilate, kernel, iterations=1)unknown = binary - sure_fgcv2.imshow('unknown',unknown)
【4】分水岭算法分割
markers = cv2.watershed(img, markers=markers)min_val, max_val, min_loc, max_loc = cv2.minmaxloc(markers)
【5】轮廓查找和标记
contours,hierarchy = cv2.findcontours(mask, cv2.retr_external, cv2.chain_approx_none) for cnt in contours: m = cv2.moments(cnt) cx = int(m['m10']/m['m00']) cx = int(m['m10']/m['m00']) cy = int(m['m01']/m['m00'])#轮廓重心 cv2.drawcontours(img,contours,-1,colors[rd.randint(0,5)],2) cv2.drawmarker(img, (cx,cy),(0,255,0),1,8,2)
方法二:轮廓凸包缺陷方法
基于轮廓凸包缺陷分割步骤如下:
【1】高斯滤波 + 二值化 + 开运算
gray = cv2.cvtcolor(img, cv2.color_bgr2gray)gray = cv2.gaussianblur(gray,(5,5),0)ret, binary= cv2.threshold(gray, 115, 255, cv2.thresh_binary) kernel = np.ones((5, 5), np.uint8)binary = cv2.morphologyex(binary, cv2.morph_open, kernel, iterations=1)cv2.imshow('thres', binary)
【2】轮廓遍历 + 筛选轮廓含有凸包缺陷的轮廓
contours,hierarchy = cv2.findcontours(binary, cv2.retr_external, cv2.chain_approx_none)for cnt in contours: hull = cv2.convexhull(cnt,returnpoints=false)#默认returnpoints=true defects = cv2.convexitydefects(cnt,hull) #print defects pt_list = [] if defects is not none: flag = false for i in range(0,defects.shape[0]): s,e,f,d = defects[i,0] if d > 4500: flag = true
【3】将距离d最大的两个凸包缺陷点连起来,将二值图中对应的粘连区域分割开,红色圆标注为分割开的部分
if len(pt_list) > 0: cv2.line(binary,pt_list[0],pt_list[1],0,2) cv2.imshow('binary2',binary)
【4】重新查找轮廓并标记结果
contours,hierarchy = cv2.findcontours(binary, cv2.retr_external, cv2.chain_approx_none)for cnt in contours: try: m = cv2.moments(cnt) cx = int(m['m10']/m['m00']) cx = int(m['m10']/m['m00']) cy = int(m['m01']/m['m00'])#轮廓重心 cv2.drawcontours(img,cnt,-1,colors[rd.randint(0,5)],2) cv2.drawmarker(img, (cx,cy),(0,0,255),1,8,2) except: pass
中兴通讯已在15个城市同步开展了5G承载试点验证
致爱好单片机学习的朋友
工业互联网是什么?到底有什么用
国产EDA迎新突破,部分工具支持5nm工艺
车载及工业用以太网的新标准:瑞萨将演示四大功能
OpenCV两种不同方法实现粘连大米分割计数
Arm携手MediaTek和vivo将TCS23运用于新一代旗舰智能手机
三星和台积电在5nm先进制程上将进行没有硝烟的战争
宏集应用丨宏集七轴机械臂,以精准力控实现柔性抛光打磨!
跨域融合——联合电子首款区域控制器顺利下线
苹果即将推出第九代iPad 搭载10.5英寸显示屏
华为P10陶瓷白真机上手图赏:美到不能呼吸!
传感器检测的三种方法解析
隐藏的冠军接插件
英特尔:Xe-HPG DG2 游戏独显正在测试中 预计2021年发货
索尼进军汽车市场,未来的“索尼汽车”简析
基于HME_P060的OLED字符显示及FUXI工程建立演示
区块链市场人才紧缺,应远近结合共同解决人才匮乏
iOS10.1/10.1.1越狱发布!iOS10.2的越狱即将来临
板对板连接器的重要作用