社区微信群开通啦,扫一扫抢先加入社区官方微信群
社区微信群
cornerHarris() 角点检测具有旋转不变特性。关于角点检测用一幅图来讲解:
窗口函数(Sobel求导中使用的窗口) :可以是正常的矩形窗口,也可以是对每一个像素给予不同权重的高斯窗口
角点检测中要使 E(μ,ν) 的值最大。这就是说必须使方程右侧的第二项的取值最大。对上面的等式进行泰勒级数展开然后再通过几步数学换算(可以参考其他标准教材),我们得到下面的等式:
E(u,v)=[uv]≈M[uv]
其中:
E(u,v)=x,y∑w(x,y)[Ix2IxIyIxIyIy2]
这里 Ix 和 Iy 是图像在 x 和 y 方向的导数。(可以使用函数 cv2.Sobel(),计算得到)详情请点击。
他们根据一个用来判定窗口内是否包含角点的等式进行打分。
R=det(M)−k(trace(M))2
其中:
det(M)=λ1λ2
trace(M)=λ1+λ2
λ1 和 λ2 是矩阵 M 的特征值:我们可以判断一个区域是否是角点,边界或者是平面。
cv2.cornerHarris(src=gray, blockSize, ksize, k, dst=None, borderType=None)
"""
cornerHarris参数:
src - 数据类型为 float32 的输入图像。(输入单通道图)
blockSize - 角点检测中要考虑的领域大小。也就是计算协方差矩阵时的窗口大小
ksize - Sobel求导中使用的窗口大小
k - Harris 角点检测方程中的自由参数,取值参数为 [0.04,0.06].
dst - 输出图像
borderType - 边界的类型
"""
示例一:
# encoding:utf-8
import cv2
import numpy as np
filename = 'D:\image_person\00001.png'
img = cv2.imread(filename)
img = cv2.resize(img, (640, 480))
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
gray = np.float32(gray)
# 输入图像必须是float32, 最后一个参数[0.04,0.06]
dst = cv2.cornerHarris(gray, 2, 3, 0.04)
cv2.imshow('dst', dst)
dst = cv2.dilate(dst, None)
img[dst > 0.01 * dst.max()] = [0, 0, 255]
cv2.imshow('img', img)
cv2.imshow('dst2', dst)
cv2.waitKey(0)
cv2.destroyAllWindows()
左侧为原图,右侧为检测之后的图像。
参数测试:(我写了两组数据测试,使大家一目了然,BlockSize ,Ksize 这两个参数的含义)
import cv2
import numpy as np
img = cv2.imread('D:\image_person\06_01.jpg')
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
gray = np.float32(gray) # cornerHarris函数图像格式为 float32
BlockSize =(2,3,4,5,7,9)
Ksize =(3,5,5,9,11,23)
for i,j in zip(BlockSize,Ksize):
dst = cv2.cornerHarris(src=gray, blockSize=i, ksize=j, k=0.04)
# 变量a的阈值为0.01 * dst.max(),如果dst的图像值大于阈值,那么该图像的像素点设为True,否则为False
# 将图片每个像素点根据变量a的True和False进行赋值处理,赋值处理是将图像角点勾画出来
a = dst>0.01 * dst.max()
img[a] = [0, 0, 255]
cv2.imshow('corners_' + str(i) + '_' + str(j), img)
cv2.waitKey(0) # 按Esc查看下一张
cv2.waitKey(0)
cv2.destroyAllWindows()
有时候我们检验时有很多角点都是粘连在一起的,通过加入非极大值抑制来进一步去除一些粘在一起的角点。也就是在一个窗口内,如果有多个角点则用值最大的那个角点,其他的角点都删除。
请看如下示例:
import cv2
import numpy as np
img = cv2.imread('./lou.png')
cv2.imshow('raw_img', img)
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
gray = np.float32(gray) # cornerHarris函数图像格式为 float32
J = (0.05,0.01,0.005)
for j in J: # 遍历设置阈值:j * dst.max()
dst = cv2.cornerHarris(src=gray, blockSize=5, ksize=7, k=0.04)
a = dst>j * dst.max()
img[a] = [0, 0, 255]
cv2.imshow('corners_'+ str(j), img)
cv2.waitKey(0) # 按Esc查看下一张
cv2.waitKey(0)
cv2.destroyAllWindows()
goodFeaturesToTrack()是cornerHarris() 函数升级版。该函数的角点检测效果与cornerHarris()函数效果差不多。
Harris 角点检测的打分公式为:
R=λ1λ2−k(λ1+λ
原文链接:https://blog.csdn.net/wsp_1138886114/article/details/90415190
站方申明:本站部分内容来自社区用户分享,若涉及侵权,请联系站方删除。
如果觉得我的文章对您有用,请随意打赏。你的支持将鼓励我继续创作!