非封闭轮廓
使用cv2.findContours函数查找轮廓,查找到的轮廓有封闭的,也有非封闭的,下面是非封闭轮廓的一些特性。
逼近多边形
cv2.approxPolyDP函数可以构造轮廓的逼近多边形。
非封闭轮廓无法用该函数生成四边形包围框:
- 精度较低时构造出异型多边形;
- 精度较高时几乎沿着轮廓构造多边形。
试验代码:
import cv2
import numpy as np
# 图像预处理
img = cv2.imread(filename, 1) # BGR图像
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
edge = cv2.Canny(gray, 160, 230)
# 查找轮廓
contours, hierarchy = cv2.findContours(edge, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
c = sorted(contours, key=cv2.contourArea, reverse=True) # 轮廓排序
# 构造逼近多边形
ep = 0.1 * cv2.arcLength(c[0],True) # 精度
approx = cv2.approxPolyDP(c[0], ep, True)
img_approx = cv2.drawContours(img.copy(),[approx],0,(0,255,0),2) # 绘制多边形
cv2.imshow("img_approx", img_approx)
cv2.waitKey(0)
cv2.destroyAllWindows()
矩形包围框
非封闭轮廓可以使用cv2.boundingRect函数构造出矩形包围框。
# 矩形包围框
x, y, w, h = cv2.boundingRect(c[0])
img_rect = cv2.rectangle(img.copy(), (x, y), (x+w, y+h), (0,255,0), 2)
cv2.imshow("img_rect", img_rect)
最小矩形包围框
非封闭轮廓可以使用cv2.minAreaRect函数构造出最小包围矩形框。
# 最小矩形包围框
ret = cv2.minAreaRect(c[0])
pts = cv2.boxPoints(ret)
pts = np.int0(pts)
img_min = cv2.drawContours(img.copy(), [pts], -1, (0,0,255), 2)
cv2.imshow("img_min", img_min)