当前位置: 首页 > news >正文

day37图像处理OpenCV

文章目录

  • 一、图像预处理
    • 19 霍夫变换
      • 19.1 理解霍夫变换
      • 19.2 (标准)霍夫直线变换
      • 19.3 统计概率霍夫直线变换
      • 19.4 霍夫圆变换

一、图像预处理

19 霍夫变换

19.1 理解霍夫变换

  • 霍夫变换是图像处理的一种技术,主要用于检测图像中的直线、圆等几何形状。基本思想就是将图像空间中的点映射到参数空间中,通过在参数空间中寻找累计最大值实现对特定形状的检测。

在这里插入图片描述

19.2 (标准)霍夫直线变换

  • 基本原理:没有考虑x=1的直线
    • 对于一条直线(不垂直于x轴的直线),都可以用 y = k x + b y=k x+b y=kx+b来表示,此时,x和y是横纵坐标。
    • 霍夫直线就是以k和b为横纵坐标。这样原直线的每个点都可以确定一条霍夫直线,并且都交于一点(k,b),该霍夫直线用 b = − x k + y b=-x k+y b=xk+y表示。
    • 那么对于一个二值化后的图形来说,其中的每一个目标像素点(x,y),都可以画一条霍夫直线。
    • 这时判断,共点的霍夫直线越多(有相同的k,b),证明许多的点在一条的普通直线上( y = k x + b y=k x+b y=kx+b)

在直角坐标系下的一个直线,在变换后的空间中仅仅表示为一点,对于变换后的空间,我们称其为霍夫空间,也就是参数空间。也就是说,直角坐标系下的一条直线对应了霍夫空间中的一个点。类似的,霍夫空间中的一条直线也对应了直角坐标系中的一个点,如下图所示:

在这里插入图片描述

  • 进阶原理:将直角坐标系转化为极坐标系

    • 然而对于x=1这种直线(垂直于x轴)来说,y已经不存在了,斜率无穷大,无法映射到霍夫空间中去;所以先将直角坐标系转化为极坐标系,然后通过极坐标系与霍夫空间进行相互转化。

      在这里插入图片描述

    • 这时,霍夫直线的r是y轴,θ是x轴;因此我们只要知道某点的x和y的坐标,就可以得到一个关于θ-ρ的表达式,如下图所示:

在这里插入图片描述

  • 语法:
    • lines=cv2.HoughLines(image, rho, theta, threshold)
      • 参数
        • image:输入边缘检测cv.Canny(gray,30,70)得到的图像
        • rho:r的精度,以像素.为单位,表示霍夫空间中每一步的距离增量, 值越大,考虑越多的线。
        • theta:角度θ的精度,通常以弧度为单位**(np.pi/180)**,表示霍夫空间中每一步的角度增量。值越小,考虑越多的线。
        • threshold:阈值,只有共点的霍夫直线的数大于阈值,该共点才会保存
      • 返回值:
        • 函数返回一个二维数组,每一行代表一条直线,返会的值是保存的共点 (θ, ρ)
  • 返回值处理:
    • 极坐标系:$ρ=x · cosθ +y · sinθ $
    • 已知 θ,ρ,再确认两个x点,就能算出两个y点,最后根据两点画直线
  • 示例:
# 读图
img = cv.imread("./images/huofu.png")
# 转灰度
gray = cv. cvtColor(img,cv.COLOR_BGR2GRAY)
# 边缘检测
dst = cv.Canny(gray,30,70)
# 霍夫直线变换
lines = cv.HoughLines(dst,0.8,np.pi/180,90)
# 遍历返回数组画直线
for line in lines:rho, theta = line[0]  # 满足的共点(θ, ρ)# 计算直线上的两个点sin_theta = np.sin(theta)cos_theta = np.cos(theta)x1,x2 = 0, img.shape[1]y1, y2 = int((rho-x1*cos_theta)/sin_theta), int((rho-x2*cos_theta)/sin_theta)# 画直线cv.line(img,(x1,y1),(x2,y2),(0,0,255),1,cv.LINE_AA)# 显示图片
cv.imshow("img",img)
cv.waitKey(0)
cv.destroyAllWindows()

19.3 统计概率霍夫直线变换

前面的方法又称为标准霍夫变换,它会计算图像中的每一个点,计算量比较大,另外它得到的是整一条线(r和θ),并不知道原图中直线的端点。所以提出了统计概率霍夫直线变换(Probabilistic Hough Transform),是一种改进的霍夫变换。

  • 改进原理:

    • 它在获取到直线之后,会检测原图中在该直线上的点,并获取到两侧的端点坐标,然后通过两个点的坐标来计算该直线的长度,通过直线长度与最短长度阈值的比较来决定该直线要不要被保留。
  • 语法:

    • lines=cv2.HoughLinesP(image, rho, theta, threshold, lines=None, minLineLength=0, maxLineGap=0)
      • 参数
        • image:输入图像,通常为二值图像,其中白点表示边缘点,黑点为背景。
        • rho:极径分辨率,以像素为单位,表示极坐标系中的距离分辨率。
        • theta:极角分辨率,以弧度为单位,表示极坐标系中角度的分辨率。
        • threshold:阈值,用于过滤掉弱检测结果,只有累计投票数超过这个阈值的直线才会被返回。
        • lines(可选):一个可初始化的输出数组,用于存储检测到的直线参数。
        • minLineLength(可选):最短长度阈值,比这个长度短的线会被排除。
        • maxLineGap(可选):同一直线两点之间的最大距离。当霍夫变换检测到一系列接近直角的线段时,这些线段可能是同一直线的不同部分。maxLineGap参数指定了在考虑这些线段属于同一直线时,它们之间最大可接受的像素间隔。
      • 返回值:
        • 返回一个二维数组,每个元素是一个包含4个元素的数组,分别表示每条直线的起始点和结束点在图像中的坐标(x1, y1, x2, y2)。
    • 示例:
    # 读图
    img = cv.imread("./images/huofu.png")
    # 转灰度
    gray = cv.cvtColor(img, cv.COLOR_BGR2GRAY)
    # 边缘检测
    dst = cv.Canny(gray, 30, 70)
    # 统计概率霍夫直线变换--这里没设置参数lines,所以后面两个参数要指定变量名
    lines = cv.HoughLinesP(dst, 0.8, np.pi / 180, 90, minLineLength=50, maxLineGap=10)
    # 遍历返回数组画直线
    for line in lines:x1, y1, x2, y2 = line[0]  # 直线的两端坐标# 画直线cv.line(img, (x1, y1), (x2, y2), (0, 0, 255), 1, cv.LINE_AA)# 显示图片
    cv.imshow("img", img)
    cv.waitKey(0)
    cv.destroyAllWindows()
    

19.4 霍夫圆变换

霍夫圆变换跟直线变换类似,它可以从图像中找出潜在的圆形结构,并返回它们的中心坐标和半径。只不过线是用(r,θ)表示,圆是用(x_center,y_center,r)来表示,从二维变成了三维,数据量变大了很多;所以一般使用霍夫梯度法减少计算量。

  • 语法

    • circles=cv2.HoughCircles(image, method, dp, minDist, param1, param2)
      • 参数
        • image:输入图像,通常是灰度图像。
        • method:使用的霍夫变换方法:霍夫梯度法,可以是 cv2.HOUGH_GRADIENT,这是唯一在OpenCV中用于圆检测的方法。
        • dp:累加器分辨率与输入图像分辨率之间的降采样比率,用于加速运算但不影响准确性。设置为1表示霍夫梯度法中累加器图像的分辨率与原图一致
        • minDist:检测到的圆心之间的最小允许距离,以像素为单位。在霍夫变换检测圆的过程中,可能会检测到许多潜在的圆心。minDist 参数就是为了过滤掉过于接近的圆检测结果,避免检测结果过于密集。当你设置一个较小的 minDist 值时,算法会尝试找出尽可能多的圆,即使是彼此靠得很近的圆也可能都被检测出来。相反,当你设置一个较大的 minDist 值时,算法会倾向于只检测那些彼此间存在一定距离的独立的圆。
        • param1param2:这两个参数是在使用 cv2.HOUGH_GRADIENT 方法时的特定参数,分别为:
          • param1(可选):阈值1,决定边缘强度的阈值。
          • param2:阈值2,控制圆心识别的精确度。较大的该值会使得检测更严格的圆。param2 通常被称为圆心累积概率的阈值。在使用霍夫梯度方法时,param2 设置的是累加器阈值,它决定了哪些候选圆点集合被认为是有效的圆。较高的 param2 值意味着对圆的检测更严格,只有在累加器中积累了足够高的响应值才认为是真实的圆;较低的 param2 值则会降低检测的门槛,可能会检测到更多潜在的圆,但也可能包含更多的误检结果。
      • 返回值:
        • 返回一个二维numpy数组,包含了所有满足条件的圆的圆心坐标和半径。
  • 示例

img = cv.imread("./images/huofu.png")
gray = cv.cvtColor(img,cv.COLOR_BGR2GRAY)
dst = cv.Canny(gray,30, 70)
# 霍夫圆变换
circles = cv.HoughCircles(dst,cv.HOUGH_GRADIENT,1,20,param2=30)
# 转整数
circles = np.int_(circles)
# 遍历画圆
for circle in circles:x,y,r = circle[0] # 圆心坐标和半径cv.circle(img,(x,y),r,(0,0,255),1,cv.LINE_AA)
cv.imshow("img",img)
cv.waitKey(0)
cv.destroyAllWindows()

相关文章:

  • Huffman(哈夫曼)解/压缩算法实现
  • 高职人工智能技术应用专业(计算机视觉方向)实训室解决方案
  • 蜜罐管理和数据收集服务器:Modern Honey Network (MHN)
  • Linux 内核网络协议栈中 inet_stream_ops 与 tcp_prot 的深度解析
  • Python----深度学习(基于深度学习Pytroch簇分类,圆环分类,月牙分类)
  • uniapp 仿企微左边公司切换页
  • 第11章 面向分类任务的表示模型微调
  • 同步定时器的用户数要和线程组保持一致,否则jmeter会出现接口不执行’stop‘和‘×’的情况
  • MySQL元数据库完全指南:探秘数据背后的数据
  • Axure PR 9 中继器 标签
  • MTKAndroid13-Launcher3 屏蔽部分app不让显示
  • 如何让 HTML 文件嵌入另一个 HTML 文件:详解与实践
  • 电脑温度怎么看 查看CPU温度的方法
  • js数据结构之栈
  • 【Java】Maven3.5.0安装
  • Qt 调试信息重定向到本地文件
  • maven依赖排查与注意点
  • Cursor如何手动添加多个大模型?
  • uni-app中获取用户实时位置完整指南:解决权限报错问题
  • uniapp中检查版本,提示升级app,安卓下载apk,ios跳转应用商店
  • 永辉超市一季度净利降近八成,未来12个月至18个月是改革成果集中释放期
  • 美联合健康集团高管枪杀案嫌疑人对谋杀指控不认罪
  • 好未来:2025财年收入增长51%,下个财年提高整体盈利能力是首要任务
  • 第六次“太空会师”,神舟二十号3名航天员顺利进驻中国空间站
  • 美媒称特朗普考虑大幅下调对华关税、降幅或超一半,外交部回应
  • 2024年上海发生科技融资997起,位于全国第一