在机器视觉开发中,直线检测是一项非常基础且重要的图像处理技术,广泛应用于工业检测、车道线识别、PCB 检测、钢板边缘检测、工件定位等场景。

OpenCV 提供了霍夫直线变换(Hough Line Transform),能够快速从边缘图像中提取直线信息。本文将介绍霍夫直线检测的基本原理、参数说明,并结合完整的 Python 示例帮助大家快速上手。


一、什么是霍夫直线检测?

霍夫变换(Hough Transform)是一种经典的特征检测算法,用于检测图像中的几何图形,如直线、圆等。

对于一条直线,我们通常使用斜率截距式表示:
y=kx+b y = kx + b y=kx+b

但是当直线接近垂直时,斜率会趋于无穷大,因此霍夫变换采用极坐标表示:
ρ=xcos⁡θ+ysin⁡θ \rho = x\cos\theta + y\sin\theta ρ=xcosθ+ysinθ
其中:

  • ρ(rho):直线到坐标原点的距离
  • θ(theta):直线法向量与 x 轴之间的夹角

图像中的每一个边缘点都会在参数空间中进行投票,当某组 (ρ, θ) 的票数足够多时,就认为检测到了一条直线。


二、霍夫直线检测流程

整个检测过程通常如下:

读取图像
    │
    ▼
灰度化
    │
    ▼
高斯滤波(可选)
    │
    ▼
Canny边缘检测
    │
    ▼
霍夫直线检测
    │
    ▼
绘制检测结果

霍夫变换并不是直接作用于原始图像,而是作用于边缘图像,因此通常都会先进行 Canny 边缘检测。


三、OpenCV 霍夫直线检测函数

OpenCV 提供了两种直线检测方式:

1、标准霍夫变换

lines = cv2.HoughLines(
    image,
    rho,
    theta,
    threshold
)

返回的是无限延长的直线。


2、概率霍夫变换(推荐)

lines = cv2.HoughLinesP(
    image,
    rho,
    theta,
    threshold,
    minLineLength,
    maxLineGap
)

返回的是线段的两个端点,更符合工业视觉的实际需求,因此实际项目中使用最多。


四、参数详解

1、rho

距离分辨率。

通常设置:

rho = 1

表示距离精度为 1 个像素。


2、theta

角度分辨率。

一般写成:

theta = np.pi / 180

表示每 1° 检测一次。

如果需要更高精度,可以设置:

theta = np.pi / 360

即每 0.5° 检测一次。


3、threshold

投票阈值。

例如:

threshold = 80

表示:

只有累计票数超过 80 才认为是一条直线。

数值越小:

  • 检测更多直线
  • 容易误检

数值越大:

  • 检测更严格
  • 容易漏检

4、minLineLength

最小线段长度。

例如:

minLineLength = 100

表示:

长度不足 100 像素的线段直接过滤。

工业视觉中通常都会设置该参数。


5、maxLineGap

允许断裂距离。

例如:

maxLineGap = 10

表示:

两段线之间如果相距不足 10 个像素,则自动连接为一条完整直线。

对于边缘存在断裂的图像非常有用。


五、基础示例

下面演示标准的霍夫直线检测流程。

import cv2
import numpy as np

# 读取图片
img = cv2.imread("line.png")

# 灰度化
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

# Canny边缘检测
edges = cv2.Canny(gray, 50, 150)

# 霍夫直线检测
lines = cv2.HoughLinesP(
    edges,
    rho=1,
    theta=np.pi / 180,
    threshold=80,
    minLineLength=50,
    maxLineGap=10
)

# 绘制结果
if lines is not None:

    for line in lines:

        x1, y1, x2, y2 = line[0]

        cv2.line(
            img,
            (x1, y1),
            (x2, y2),
            (0, 255, 0),
            2
        )

cv2.imshow("Result", img)
cv2.waitKey(0)
cv2.destroyAllWindows()

运行后即可在原图上看到检测出的直线。


六、计算直线长度

霍夫变换返回的是两个端点,因此可以直接计算线段长度。

length = np.sqrt((x2 - x1) ** 2 + (y2 - y1) ** 2)

print(length)

这在工业检测中十分常见,例如:

  • 裂纹长度
  • 边缘长度
  • 焊缝长度

七、计算直线角度

直线角度可通过反正切计算。

angle = np.degrees(
    np.arctan2(
        y2 - y1,
        x2 - x1
    )
)

print(angle)

返回值范围:

[-180°,180°]

通常工业视觉会转换为:

0~180°

方便进行角度判定。


八、实际案例:检测工件边缘

工业检测中,可以结合 Canny 与霍夫变换快速提取工件边缘。

import cv2
import numpy as np

img = cv2.imread("part.png")

gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

gray = cv2.GaussianBlur(gray, (5,5), 0)

edges = cv2.Canny(gray, 80, 150)

lines = cv2.HoughLinesP(
    edges,
    1,
    np.pi/180,
    threshold=60,
    minLineLength=120,
    maxLineGap=15
)

if lines is not None:

    for line in lines:

        x1,y1,x2,y2 = line[0]

        cv2.line(
            img,
            (x1,y1),
            (x2,y2),
            (0,255,0),
            2
        )

cv2.imshow("Edge Detection",img)
cv2.waitKey(0)
cv2.destroyAllWindows()

实际项目中,通常会先进行 ROI 裁剪,再执行霍夫直线检测,以提高检测速度和稳定性。


九、工业视觉中的应用

霍夫直线检测在工业领域应用十分广泛,例如:

  • PCB 板边缘检测
  • 钢板定位
  • 工件姿态校正
  • 刀具角度测量
  • 焊缝检测
  • 激光条纹检测
  • 产品边缘定位
  • 车道线识别

通常不会单独使用,而是结合滤波、阈值分割、形态学处理等预处理算法共同完成检测任务。


十、霍夫直线检测优缺点

优点:

  • 算法成熟,OpenCV 内置实现。
  • 检测速度快,适合实时应用。
  • 能同时检测多条直线。
  • 对一定程度的噪声具有较好的鲁棒性。

缺点:

  • 对边缘质量依赖较高。
  • 参数需要根据实际场景调整。
  • 对复杂背景容易产生误检。
  • 曲线或不规则边缘无法直接检测。

十一、总结

霍夫直线检测是 OpenCV 中最经典的几何特征检测算法之一,也是机器视觉开发中的基础工具。实际工程中,一般采用 Canny 边缘检测 + 概率霍夫变换(HoughLinesP) 的组合方案,并结合 ROI、滤波和形态学处理,提高检测精度和运行效率。

对于工业视觉项目,霍夫直线检测不仅可以完成目标定位,还能够进一步计算直线长度、角度和位置,为尺寸测量、姿态校正和缺陷检测等后续任务提供可靠的数据支持。

Logo

CANN开发者社区旨在汇聚广大开发者,围绕CANN架构重构、算子开发、部署应用优化等核心方向,展开深度交流与思想碰撞,携手共同促进CANN开放生态突破!

更多推荐