python Opencv 常用基础函数:霍夫圆检测

1.cv.HoughCircles:圆形霍夫变换-OpenCV

基本原理:

对于圆周上的每一个点,求其梯度,根据梯度可做出关于此点的切线,与切线垂直的方向就是梯度样方向,每个点的梯度方向的交点就是圆心,然后根据圆心的位置可以确定其半径。

circles=cv.HoughCircles(image, method, dp, minDist[, param1[, param2[, minRadius[, maxRadius]]]]])
 
image:灰度图像
method:一般为cv.HOUGH_GRADIENT
dp:累加器分辨率与图像分辨率的反比,一般为1
minDist:不同圆心直接的最小距离,太大会遗漏一些圆形,太小会产生许多无关的圆
param1:传递给 canny 边缘检测算子的高阀值,而低阀值为高阀值的一半
param2:是检测阶段圆心的累加阀值。越小可以检测到更多的假圆。越大能通过检测的圆就更加接近完美的圆形。
minRadius:最小半径
maxRadius:最大半径


2.OpenCV circle()函数

cvCircle(CvArr* img, CvPoint center, int radius, CvScalar color, int thickness=1, int lineType=8, int shift=0)

img为源图像指针

center为画圆的圆心坐标

radius为圆的半径

color为设定圆的颜色,规则根据B(蓝)G(绿)R(红)

thickness 如果是正数,表示组成圆的线条的粗细程度。否则,-1表示圆是否被填充

line_type 线条的类型。默认是8

shift 圆心坐标点和半径值的小数点位数

以下为在圈出水表圆盘过程的代码,将表盘框出然后裁剪并重新设置大小为600*600,这是学习的过程,可能一些用法比较繁琐

img_list = os.listdir(data_list_path)
#for i in range(len(img_list)):
i=140
img=cv.imread(data_list_path+'/'+img_list[i])
imgcopy = img.copy()
gray = cv.cvtColor(imgcopy,cv.COLOR_BGR2GRAY)
dst = cv.calcHist([gray], [0], None, [256], [0, 256])
gray1 = cv.equalizeHist(gray)
dst1 = cv.calcHist([gray1], [0], None, [256], [0, 256])
# plt.subplot(211), plt.plot(dst)
# #plt.subplot(312), plt.plot(dst1)
# plt.subplot(212), plt.plot(dst1)
# plt.show()
print(np.shape(gray),min(np.shape(gray)))
sy,sx=np.shape(gray)
td=min(np.shape(gray))
minD=int(td/4)
minR=int(td/4)
maxR=int(td/2)
# 将图进行中值模糊,检测圆的效果更好
gray = cv.medianBlur(gray,5)
th=170
err=0
#thresh1=cv.adaptiveThreshold(gray, 255, cv.ADAPTIVE_THRESH_MEAN_C, cv.THRESH_BINARY,9, 2)
ret2,thresh2=cv.threshold(gray,th,255,cv.THRESH_TRUNC)

#binary = cv.adaptiveThreshold(gray, 127, cv.ADAPTIVE_THRESH_GAUSSIAN_C, cv.THRESH_BINARY, 9, 30)

circles = cv.HoughCircles(thresh2,cv.HOUGH_GRADIENT,dp=1,minDist=minD,
                          param1=50,param2=60
                          ,minRadius=minR,maxRadius=maxR)
try:
 # 将变换后的浮点值转换为整数
    detected_circles = np.int16(np.around(circles))
except TypeError:
    err=1
print(np.shape(detected_circles)[1])
while err==1 or np.shape(detected_circles)[1]!=1:
    print('running')
    th-=10
    ret2, thresh2 = cv.threshold(gray, th, 255, cv.THRESH_TRUNC)

    # binary = cv.adaptiveThreshold(gray, 127, cv.ADAPTIVE_THRESH_GAUSSIAN_C, cv.THRESH_BINARY, 9, 30)

    circles = cv.HoughCircles(thresh2, cv.HOUGH_GRADIENT, dp=1, minDist=minD,
                              param1=50, param2=60
                              , minRadius=minR, maxRadius=maxR)
    try:
        # 将变换后的浮点值转换为无符号整数
        detected_circles = np.int16(np.around(circles))
    except TypeError:
        err = 1
    else:
        err=0
#c=c.append(np.shape(detected_circles))
print(np.shape(detected_circles)[1])
print(np.shape(detected_circles),detected_circles)
# if (len(detected_circles)!=1):
#     continue
for (x,y,r) in detected_circles[0,:]:
    cv.circle(imgcopy,(x,y),r,(0,255,0),3)
    #画个圆心
    cv.circle(imgcopy,(x,y),2,(0,255,255),3)
x1=(x-r) if (x-r)>0 else 0
x2=(x+r) if (x+r)<sx else sx
y1=(y-r) if (y-r)>0 else 0
y2=(y+r) if (y+r)<sy else sy
print((x1,x2),(y1,y2))
cropImg = img[y1:y2, x1:x2]


 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值