2024-08-15-opencv-python-霍夫变换直线检测
opencv-python 霍夫变换直线检测
文章目录
原理
霍夫变换(Hough Transform)是一种在图像处理中用来识别图像中直线、圆和其他形状的数学变换,是Hough在1962年提出的。其核心思想是将图像中的点映射到一个参数空间,这个空间中涵盖了某个几何形状的所有参数。通过这种变换,可以将图像中的点对应到参数空间中的线或圆上,从而实现对直线和圆的检测。
霍夫变换的基本步骤通常包括:
边缘检测:首先,使用Canny边缘检测器或其他边缘检测算法来检测图像中的边缘点。
参数空间初始化:创建一个参数空间,对于直线检测,参数空间通常是一个角度
θ \theta
θ 和距离
θ \theta
θ 的笛卡尔网格;对于圆检测,参数空间通常是一个半径
r r
r 和圆心角度
θ \theta
θ 的极坐标网格。
投票过程:对于检测到的每个边缘点,计算它在参数空间中对应的所有可能的线或圆的参数。这些参数代表了图像空间中所有可能的几何形状。对于每个参数,进行累加投票,即在参数空间中对应的线或圆的位置增加一个计数。
阈值化:设定一个阈值,只保留投票数超过阈值的参数。这样可以排除噪声和边缘点引起的干扰。
参数解码:最后,将参数空间中投票最多的点解码回图像空间,这些点就是检测到的直线或圆的参数。
霍夫变换的直线检测结果由
( ρ , θ ) (\rho, \theta)
(
ρ
,
θ
) 来表示,其中
ρ \rho
ρ 表示直线与坐标原点
( 0 , 0 ) (0,0)
(
0
,
0
) 的距离,
θ \theta
θ 是直线的垂线与
x x
x 轴的夹角。从而直线方程可表示为点法式
x cos θ + y sin θ − ρ
0 x\cos\theta+y\sin\theta-\rho=0
x
cos
θ
y
sin
θ
−
ρ
=
0
对于尺寸为
m m
m 行
n n
n 列的图像来说,四个边框分别是
x
0 , x
n , y
0 , y
m x=0, x=n, y=0, y=m
x
=
0
,
x
=
n
,
y
=
0
,
y
=
m ,记
c
cos θ , s
sin θ c=\cos\theta, s=\sin\theta
c
=
cos
θ
,
s
=
sin
θ ,则直线与四个边框的交点分别为
( 0 , ρ s ) ( n , ρ − n c s ) ( ρ c , 0 ) ( ρ − m s c , m ) \begin{matrix} (0, \frac{\rho}{s})&(n, \frac{\rho-nc}{s})\ (\frac{\rho}{c}, 0)&(\frac{\rho-ms}{c}, m)\ \end{matrix}
(
0
,
s
ρ
)
(
c
ρ
,
0
)
(
n
,
s
ρ
−
n
c
)
(
c
ρ
−
m
s
,
m
)
实战
通过opencv中的直线检测函数,可得到如下检测结果。
代码如下。
from scipy.misc import ascent
import numpy as np
import cv2 as cv
from matplotlib import pyplot as plt
img = ascent().astype(np.uint8)
m, n = img.shape
edges = cv.Canny(img, 50, 150, apertureSize = 3)
lines = cv.HoughLines(edges,1.5,np.pi/180,200)
fig, ax = plt.subplots(1,2)
ax[0].imshow(img, cmap='gray')
for line in lines:
rho,theta = line[0]
c = np.cos(theta)
s = np.sin(theta)
xs = [0, n, rho/c, (rho-m*s)/c]
print(xs)
ys = [rho/s, (rho-n*c)/s, 0, m]
i1, i2 = np.argsort(xs)[1:3]
ax[0].plot([xs[i1], xs[i2]], [ys[i1], ys[i2]], ls='--')
ax[1].plot([xs[i1], xs[i2]], [ys[i1], ys[i2]], ls='--')
plt.grid()
plt.show()
【HoughLines】就是opencv中的基于霍夫变换的直线检测函数,其输入的四个参数分别是待检测图像、以像素为单位的距离精度
p r p_r
p
r
、以弧度为单位的角度精度 KaTeX parse error: Undefined control sequence: \tehta at position 3: p_\̲t̲e̲h̲t̲a̲ 以及累加平面的阈值参数。
p r , p θ p_r, p_\theta
p
r
,
p
θ
这两个值设得越大,则会检查出越多的直线。
68747470733a2f2f62:6c6f672e6373646e2e6e65742f6d305f33373831363932322f:61727469636c652f64657461696c732f313336353738353333