python - 将对象掩码应用于 LBP 计算

标签 python opencv image-processing feature-extraction lbph-algorithm

我看到很多文章将 lbp 应用于基于纹理的图像分类。我只是想知道有关这项技术的三件事,但我无法从 Google 中找到明确的答案:

  1. 算法如何计算周围没有足够相邻像素的图像边界像素的 lbp。

  2. 如果我们有八个相邻像素,那么中心像素将有 256 个图案(如果使用 uniform 则为 59 个)。但是如果我们增加相邻像素的大小(例如 8 或 10),那么图案的数量也会增加,对吗?在那种情况下,它如何影响直方图计算?

  3. 我们怎样才能只计算物体的 lbp。特别是,如果我们想比较图像中的物体,我们只需要计算物体的 lbp 和直方图。我已经尝试通过使用 opencv 直方图(它支持掩码和 numpy 直方图不支持掩码)到 lbp 输出来实现这个想法,但它没有用。关于如何基于掩码过滤 lbp 数组的任何想法,然后我们可以找到直方图。

谢谢。

最佳答案

  1. 边界像素通常会被丢弃(看看第一个提出 LBP 的研究小组开发的 Matlab implementation)。在其他实现中(例如,参见 Python 的 scikit-learn )添加了黑色边框。

  2. P 像素的局部邻域生成 2P-bin 直方图。如果设置 P=10,则特征向量将有 1024 个分量。

  3. 这个玩具示例向您展示了如何从 LBP 直方图计算中过滤掉不需要的图像区域:

    import numpy as np
    from skimage.feature.texture import local_binary_pattern
    
    P, R = 8, 1
    dim = 2**P
    img = np.asarray([[5, 5, 5, 5], [5, 99, 100, 5], [5, 5, 5, 5]]], dtype=np.uint8)
    mask = img > 5
    codes = local_binary_pattern(img, P, R)
    hist, _ = np.histogram(codes[mask], bins=np.arange(dim+1), range=(0, dim))
    

    演示

    In [97]: img
    Out[97]: 
    array([[  5,   5,   5,   5],
           [  5,  99, 100,   5],
           [  5,   5,   5,   5]], dtype=uint8)
    
    In [98]: codes
    Out[98]: 
    array([[ 193.,  241.,  241.,  112.],
           [ 199.,    1.,    0.,  124.],
           [   7.,   31.,   31.,   28.]])
    
    In [99]: mask
    Out[99]: 
    array([[False, False, False, False],
           [False,  True,  True, False],
           [False, False, False, False]], dtype=bool)
    
    In [100]: hist
    Out[100]: 
    array([1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
           0, 0, 0], dtype=int32)
    

编辑

这是一个更现实的例子,正如您在评论中所要求的那样:

import numpy as np
from skimage import io
from skimage.feature.texture import local_binary_pattern
import matplotlib.pyplot as plt

P = 8
R = 1
dim = 2**P
h_bins = np.arange(dim+1)
h_range = (0, dim)

img = io.imread('/image/6ESoP.png')
mask = (img > 0)
codes = local_binary_pattern(img, P, R)
h_img, _ = np.histogram(codes.ravel(), bins=h_bins, range=h_range)
h_masked, _ = np.histogram(codes[mask], bins=h_bins, range=h_range)
h_img = h_img/h_img.sum(dtype=np.float)
h_masked = h_masked/h_masked.sum(dtype=np.float)

f, [[ax0, ax1], [ax2, ax3]] = plt.subplots(2, 2)
ax0.imshow(img, cmap=plt.cm.gray)
ax0.axis('off')
ax0.set_title('Image')
ax1.imshow(mask, cmap=plt.cm.gray)
ax1.axis('off')
ax1.set_title('Mask')
ax2.plot(h_img)
ax2.set_title('LBP of image')
ax3.plot(h_masked)
ax3.set_title('LBP of ROI')
plt.show(f)

Results

关于python - 将对象掩码应用于 LBP 计算,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48413398/

相关文章:

python - 如何重新索引多索引 pandas 数据框?

python - python中蛋白质的分子量总和

python - Flask 在虚拟环境中不起作用

java - 在 Android 上使用带有 OpenCV 的相机 LED 闪光灯

python - python处理大量图片的技巧

python - 将多边形框添加到cartopy python

android - Opencv 4.1.1 Android 链接错误

opencv - 使用 mogrify 将 jpg 无损转换为 png

c# - 从 UWP 中的 BitmapImage 或流获取 IntPtr 值

html - 渲染 svg 与图像