前言:今天是团队的集训日,自己选了HAAR特征的课题来研究,参考了很多博文,都没给出代码实现,遂贡献下自己的代码吧。关于HAAR特征网上已经有很多博文解释的很好了,我肯定是没他们写得好啦,所以我会在下面给出我看到最好的文章。而且最近在看机器学习的内容,博客更新的有点慢。
推荐参考博客连接:http://blog.csdn.net/jing_xin/article/details/17383161
关于积分图:图一是参考博客里的,图二是自己画的,可以帮助你们理解下我的代码
图一
图二
关于代码:我只实现了横向的比较,就是下图两矩形类右边的那个,其他情况类似
import cv2 as cv
#积分图
def intergralMat(input = [],weigth = 0 ,height = 0):
output = []
output.clear()
columnSum = [0 for i in range(weigth)]
for i in range(height):
output.append([0 for x in range(weigth)])
for j in range(weigth):
if j == 0:
columnSum[j] = int(input[i][j])
else:
columnSum[j] = columnSum[j-1] + int(input[i][j])
if i == 0:
output[i][j] = columnSum[j]
else:
output[i][j] = output[i-1][j] + columnSum[j]
return output
#哈尔图,默认size=1,deep=2
def myHaar(interM = [],weigth = 0,height = 0,size = 1,deep = 2):
dst = []
for i in range(height - deep + 1):
dst.append([0 for x in range(weigth - size)])
for j in range(weigth - 2*size +1):
whithe,black = (0,0)
if j == 0 and i==0:
whithe = int(interM[i+deep-1][j+size-1])
elif i!=0 and j==0:
whithe = int(interM[i + deep - 1][j + size - 1]) - int(interM[i - 1][j + size -1])
elif i == 0 and j != 0:
whithe = int(interM[i+deep-1][j+size-1]) - int(interM[i+1][j-1])
else:
whithe = int(interM[i+deep-1][j+size-1]) + int(interM[i-1][j-1]) - int(interM[i+1][j-1]) - int(interM[i -1][j+ size -1])
_i = i
_j = j + size
if _i == 0:
black = int(interM[_i+deep-1][_j+size-1]) - int(interM[_i+1][_j-1])
else:
black = int(interM[_i+deep-1][_j+size-1]) + int(interM[_i-1][_j-1]) - int(interM[_i+1][_j-1]) - int(interM[_i - 1][_j+ size -1])
dst[i][j] = black - whithe
return dst
def main():
src = cv.imread('1.jpg')
tmp = src.copy()
# 分裂出三通道。这里只取b通道来进行分析,实际应该是分析三个通道,再合并
b, g, r = cv.split(src)
# 用于得到图像的宽高
_w = len(b[0])
_h = len(b)
in_b = intergralMat(b, _w, _h)
Haar_b = myHaar(in_b, _w, _h)
dst = []
for x in range(len(Haar_b)):
dst.append([])
for y in range(len(Haar_b[0])):
if Haar_b[x][y] > 0:
dst[x].append(255)
else:
dst[x].append(0)
for x in range(len(dst)):
for y in range(len(dst[0])):
f = dst[x][y]
tmp[x, y] = [f, f, f]
cv.imshow('src', src)
cv.imshow('test', tmp)
cv.waitKey()
main()
效果图:由于只实现了横向的比较,所以只有竖直的线可以提取特征