python 生成任意形状的凸包图代码


Posted in Python onApril 16, 2020

一、效果图:

在左图的白色区域周围,画任意形状的凸包图。

python 生成任意形状的凸包图代码

二、代码

import cv2
import numpy as np
 
def generate_poly(image, n, area_thresh):
 """
 随机生成凸包
 :param image: 二值图
 :param n: 顶点个数
 :param area_thresh: 删除小于此面积阈值的凸包
 :return: 凸包图
 """
 row, col = np.where(image[:, :, 0] == 255) # 行,列
 point_set = np.zeros((n, 1, 2), dtype=int)
 for j in range(n):
  index = np.random.randint(0, len(row))
  point_set[j, 0, 0] = col[index]
  point_set[j, 0, 1] = row[index]
 hull = []
 hull.append(cv2.convexHull(point_set, False))
 drawing_board = np.zeros(image.shape, dtype=np.uint8)
 cv2.drawContours(drawing_board, hull, -1, (255, 255, 255), -1)
 cv2.namedWindow('drawing_board', 0), cv2.imshow('drawing_board', drawing_board), cv2.waitKey()
 
 # 如果生成面积过小,重新生成
 if cv2.contourArea(hull[0]) < area_thresh:
  drawing_board = generate_poly(image, n, area_thresh)
 
 # 如果生成洞,重新生成
 is_hole = image[drawing_board == 255] == 255
 if is_hole.all() == True: # 洞,则drawing_board所有为255的地方,image也是255,all()即为所有位置
  drawing_board = generate_poly(image, n, area_thresh)
 return drawing_board
 
 
img = np.zeros((256, 256, 3), np.uint8)
cv2.circle(img, (100, 100), 50, (255, 255, 255), -1)
cv2.namedWindow('img', 0), cv2.imshow('img', img), cv2.waitKey()
 
img_hull = generate_poly(img, 8, 100)
cv2.namedWindow('img_hull', 0), cv2.imshow('img_hull', img_hull), cv2.waitKey()

补充知识:opencv python 轮廓特征/凸包/外接矩形/外接圆/拟合矩形/拟合直线/拟合圆

Contour Features

1 图像的矩

cv2.moments()

图像的矩可以帮助计算物体的某些特征,如对象的质心,对象的区域等.

代码:

import cv2
import numpy as np
 
img = cv2.imread('img7.png',0)
ret,thresh = cv2.threshold(img,127,255,0)
im2,contours,hierarchy = cv2.findContours(thresh, 1, 2)
 
cnt = contours[0]
M = cv2.moments(cnt)
print( M )

输出:

{'m00': 283.0, 'm10': 8260.666666666666, 'm01': 34747.666666666664, 'm20': 251349.8333333333, 'm11': 1008063.0, 'm02': 4274513.166666666, 'm30': 7941981.4, 'm21': 30484543.9, 'm12': 123258620.46666667, 'm03': 526819846.70000005, 'mu20': 10223.989595602674, 'mu11': -6208.702394974302, 'mu02': 8080.874165684916, 'mu30': 8302.495426246896, 'mu21': -14552.154961312423, 'mu12': 11791.528133469663, 'mu03': -3268.923251092434, 'nu20': 0.12765785058625623, 'nu11': -0.07752253611575, 'nu02': 0.10089867729257346, 'nu30': 0.006162296011483629, 'nu21': -0.010800931752771139, 'nu12': 0.008751933371317017, 'nu03': -0.0024262672459139235}

此刻,可以提取有用的数据,如面积,质心等.

质心由关系给出:

cx = int(M['m10']/M['m00'])
cy = int(M['m01']/M['m00'])

2轮廓面积

cv2.contourArea(contour[, oriented])

3轮廓周长

cv2.arcLength(curve, closed)

第二个参数指定形状是否为闭合轮廓

4轮廓近似

它根据我们指定的精度将轮廓形状近似为具有较少顶点数的另一个形状.它是Douglas-Peucker算法的一种实现方式.

cv2.approxPolyDP(curve, epsilon, closed[, approxCurve])

第二个参数epsilon,它是从轮廓到近似轮廓的最大距离.第三个参数指定曲线是否闭合.

下面,在第二幅图像中,绿线表示epsilon =弧长的10%的近似曲线. 第三幅图像显示相同的epsilon =弧长的1%.

代码:

import cv2
import numpy as np
 
img = cv2.imread('img8.png')
cv2.imshow('src',img)
imgray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
ret, thresh = cv2.threshold(imgray, 127, 255, 0)
im2, contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
cnt = contours[1]
 
epsilon = 0.1*cv2.arcLength(cnt,True)
approx = cv2.approxPolyDP(cnt,epsilon,True)
cv2.polylines(img, [approx], True, (0, 0, 255), 2)
 
cv2.imshow('show',img)
cv2.waitKey()

python 生成任意形状的凸包图代码

5凸包

凸包看起来类似轮廓近似,但是它不是(两者在某些情况下可能提供相同的结果).

convexHull(points[, hull[, clockwise[, returnPoints]]]):检查曲线的凸性缺陷并进行修正.

points:传入的轮廓

hull:输出

clockwise:方向标志,如果为True,则顺时针方向输出凸包.

returnPoints:默认情况下为True,然后它返回hull points的坐标; 如果为False,则返回与hull points对应的轮廓点的索引

下面的手形图像. 红线表示手的凸包, 双面箭头标记显示凸起缺陷.

python 生成任意形状的凸包图代码

代码:

import cv2
import numpy as np
 
img = cv2.imread('img8.png')
 
imgray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
ret, thresh = cv2.threshold(imgray, 127, 255, 0)
im2, contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
cnt = contours[1]
 
hull = cv2.convexHull(cnt)

returnPoints = True,得到以下值:

array([[[192, 135]],
  [[ 9, 135]],
  [[ 9, 12]],
  [[192, 12]]], dtype=int32)

如果想找到凸性缺陷,需要传递returnPoints = False,得到以下结果:

array([[129],
  [ 67],
  [ 0],
  [142]], dtype=int32)

这些是轮廓中相应点的索引,检查第一个值:

cnt[129]
Out[3]: array([[192, 135]], dtype=int32)

与第一个结果相同.

6 检查凸性

cv2.isContourConvex(contour):检查曲线是否凸起

7 外接矩形

7.1 直边外接矩形

它是一个直的矩形,它不考虑对象的旋转。因此,边界矩形的面积不会最小.

cv.boundingRect()

设(x,y)为矩形的左上角坐标,(w,h)为宽度和高度

代码:

import cv2
import numpy as np
 
img = cv2.imread('img7.png')
 
imgray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
ret, thresh = cv2.threshold(imgray, 127, 255, 0)
im2, contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
cnt = contours[0]
 
x,y,w,h = cv2.boundingRect(cnt)
cv2.rectangle(img,(x,y),(x+w,y+h),(0,255,0),2)
 
cv2.imshow('show',img)
cv2.waitKey()

python 生成任意形状的凸包图代码

7.2 最小外接矩形

cv.minAreaRect返回一个Box2D结构,其中包含以下detals - (center(x,y),(width,height),rotation of rotation)

cv.boxPoints画上述矩形.

代码:

rect = cv2.minAreaRect(cnt)
box = cv2.boxPoints(rect)
box = np.int0(box)
cv2.drawContours(img,[box],0,(0,0,255),2)

python 生成任意形状的凸包图代码

8 最小封闭圈

(x,y),radius = cv2.minEnclosingCircle(cnt)
center = (int(x),int(y))
radius = int(radius)
cv2.circle(img,center,radius,(0,255,0),2)

python 生成任意形状的凸包图代码

9 拟合椭圆

ellipse = cv2.fitEllipse(cnt)
cv2.ellipse(img,ellipse,(0,255,0),2)

python 生成任意形状的凸包图代码

10 拟合直线

rows,cols = img.shape[:2]
[vx,vy,x,y] = cv2.fitLine(cnt, cv2.DIST_L2,0,0.01,0.01)
lefty = int((-x*vy/vx) + y)
righty = int(((cols-x)*vy/vx)+y)
cv2.line(img,(cols-1,righty),(0,lefty),(0,255,0),2)

python 生成任意形状的凸包图代码

以上这篇python 生成任意形状的凸包图代码就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
在GitHub Pages上使用Pelican搭建博客的教程
Apr 25 Python
python通过socket查询whois的方法
Jul 18 Python
python XlsxWriter模块创建aexcel表格的实例讲解
May 03 Python
Python打包方法Pyinstaller的使用
Oct 09 Python
pygame实现雷电游戏雏形开发
Nov 20 Python
Python弹出输入框并获取输入值的实例
Jun 18 Python
python自带tkinter库实现棋盘覆盖图形界面
Jul 17 Python
Python json转字典字符方法实例解析
Apr 13 Python
如何解决cmd运行python提示不是内部命令
Jul 01 Python
Python开发工具Pycharm的安装以及使用步骤总结
Jun 24 Python
Python tensorflow卷积神经Inception V3网络结构
May 06 Python
python中pd.cut()与pd.qcut()的对比及示例
Jun 16 Python
Python telnet登陆功能实现代码
Apr 16 #Python
基于python 凸包问题的解决
Apr 16 #Python
python实现交并比IOU教程
Apr 16 #Python
python 弧度与角度互转实例
Apr 15 #Python
使用Python三角函数公式计算三角形的夹角案例
Apr 15 #Python
Python selenium自动化测试模型图解
Apr 15 #Python
python简单实现最大似然估计&amp;scipy库的使用详解
Apr 15 #Python
You might like
PHP图形操作之Jpgraph学习笔记
2015/12/25 PHP
javascript 鼠标拖动图标技术
2010/02/07 Javascript
求数组最大最小值方法适用于任何数组
2013/08/16 Javascript
js实现仿Windows风格选项卡和按钮效果实例
2015/05/13 Javascript
javascript数组随机排序实例分析
2015/07/22 Javascript
JavaScript数据类型判定的总结笔记
2015/07/31 Javascript
跟我学习javascript的基本类型和引用类型
2015/11/16 Javascript
js实现跨域的多种方法
2015/12/25 Javascript
JavaScript toUpperCase()方法使用详解
2016/08/26 Javascript
jQuery给指定的table动态添加删除行的操作方法
2016/10/12 Javascript
解决vue里碰到 $refs 的问题的方法
2017/07/13 Javascript
浅谈Vue父子组件和非父子组件传值问题
2017/08/22 Javascript
详解基于Vue+Koa的pm2配置
2017/10/24 Javascript
JS实现关键词高亮显示正则匹配
2018/06/22 Javascript
解决jquery有正确返回值但不执行success函数的问题
2018/08/20 jQuery
详解Puppeteer前端自动化测试实践
2019/02/21 Javascript
基于vue框架手写一个notify插件实现通知功能的方法
2019/03/31 Javascript
vue中根据时间戳判断对应的时间(今天 昨天 前天)
2019/12/20 Javascript
vue基于better-scroll仿京东分类列表
2020/06/30 Javascript
React+EggJs实现断点续传的示例代码
2020/07/07 Javascript
解决vue-router路由拦截造成死循环问题
2020/08/05 Javascript
[01:30]我们共输赢 完美世界城市挑战赛开启全新赛季
2019/04/19 DOTA
python实现求最长回文子串长度
2018/01/22 Python
Pandas之MultiIndex对象的示例详解
2019/06/25 Python
新手入门学习python Numpy基础操作
2020/03/02 Python
Python实现粒子群算法的示例
2021/02/14 Python
一款基于css3麻将筛子3D翻转特效的实例教程
2014/12/31 HTML / CSS
canvas里面如何基于随机点绘制一个多边形的方法
2018/06/13 HTML / CSS
HTML5之消息通知的使用(Web Notification)
2018/10/30 HTML / CSS
ktv收银员岗位职责
2013/12/16 职场文书
小学端午节活动方案
2014/03/13 职场文书
教师师德承诺书
2014/03/26 职场文书
禁毒主题班会教案
2015/08/14 职场文书
纪检干部学习心得体会
2016/01/23 职场文书
golang内置函数len的小技巧
2021/07/25 Golang
Python可视化学习之matplotlib内置单颜色
2022/02/24 Python