考虑3x3的LBP operator。
计算方法很简单,在边缘部分的处理方式一般从第二行和第二列开始,所以便最外面一层像素是没有经过LBP处理的。这个影响不大。
LBP处理之后的像素值还是从0~255的,所以直观上,选择一个区域(整体或者局部),直方图的bin应该有256个。但假如我们选择的区域是16x16或者8x8,这样像素如果分布在256个区间里的话,一般会有很多bin是空的,增加了无用的信息,同时也浪费了不必要的处理时间。后来有人提出了一个uniform pattern,意思是比如3x3的operator周围一圈有8个像素,和中间元素比较之后他们不是0就是1了,把他们看成一个圈,相邻的元素从0到1或者从1到0表示一个跳变,uniform pattern的指那种跳变不超过两个的pattern,比如0000000,11111111,00111110这些都是uniform pattern,有人统计说,LBP里面uniform pattern占到所有pattern元素的85%~90%,于是乎,在进行LBP处理之后,很多人就将uniform pattern作为处理的主要对象,在0~255这些二进制中uniform pattern有多少个呢?下面给出了一个列表:
0,1,2, 3, 4, 6,7,8, 12,14,15, 16,24, 28, 30,31, 32, 48, 56, 60,62, 63,64, 96,112,120, 124, 126, 127, 128,129, 131, 135, 143, 159, 191, 192, 193, 195, 199,207, 223, 224, 225, 227, 231, 239, 240, 241, 243,247, 248, 249, 251, 252, 253, 254, 255
数一数,一共是58个,一般来说我们得到了大部分但是又不想割舍小部分,怎么处理剩下的像素值?流行(我没有找到好的解释)的做法是将剩下像素所有的像素值全都置于58,而之前的58个像素值分别被mapping到了0~57,加起来就构成了59个bin。
对于LBP为啥有59个bin我之前也有些不理解,网上这方面的资料也少,所以写在这里,做个笔记。
update:
按照红色标记的顺序
0. 当然,最流行的做法是3x3,但是提醒一下,3x3这个做法并不是理论上最好的。
1. 其实有的实现是在外圈填补一圈像素再进行处理,不过对于LBP这种局部算子来说,对整体没什么影响。
2. 我说16x16或者8x8在这里可能是个巧合,这些是经验做法,真正用的时候还需要去衡量,其实任何形状都可以有。
3. 85%~90%在实际应用中来看,似乎挺可靠了。有时候会问,为什么我们只用了58(+1)/256的信息,却自以为得到了85%~90%的信息量。
4. 这里是错的,数字只有57个,貌似我弄丢了一个,我得去看看是哪一个,等着第二次update,(update:已经补上)
5. 有些实现里只使用了58个bin(比如说vlfeat),其实我还有一个疑问,这些uniform pattern直接有的相差1,有的相差到了8,这么简单的映射到连续的0~57里面……有没有更加妥当的方法呢?