简介
给定一张灰度图和一系列 bounding boxes,每个bounding box(bbox) 通过 [left, top, right, down]
编码,计算每个 bbox
内部像素的均值和方差。
直观的思路是对每个bbox
计算均值然后计算方差,每一个的时间复杂度为 O ( k ⋅ w ⋅ h ) O(k\cdot w\cdot h) O(k⋅w⋅h) 其中 k k k 是一个常量。当 bbox
很多的时候,时间复杂度过高。 计算方差肯定绕不过均值,先思考如何快速计算均值。
Haar 特征
本科的时候学过 VJ-Detector
,具体原理已经忘掉了,但记得有一个haar可以快速计算区域内像素质和。思路类似二维前缀和。
-------------------y
|
| A-------B
| | |
| | |
|. C-------D
|
x
如图,我们定义:
h a a r ( x , y ) = ∑ i = 0 x ∑ j = 0 y I ( i , j ) haar(x, y) = \sum_{i = 0}^{x}\sum_{j = 0}^{y}I(i, j) haar(x,y)=i=0∑xj=0∑yI(i,j)
那么图中A, B, C, D
构成的面积可以表达为
sum_ = haar[Dx][Dy] - haar[Bx - 1][By] - haar[Cx][Cy - 1] - haar[Ax - 1][Ay - 1]
同时像素的个数可以被表达为
area = (D_x - A_x + 1) * (D_y - D_y + 1)
这样构造好了haar
以后,能够很快的计算出均值,代码如下,没有经过测试,但是原理是没有问题的:
def mean_(img, bboxes):
# bboxes 为bbox 构成的列表,bbox通过[left top right down] 编码
if len(img) == 0:
return None
row, col = len(img), len(img[0])
haar = [img[i][:] for i in range(row)]
# 构造积分图
for i in range(row):
for j in range(col):
if i == 0:
haar[i][j] += haar[i