【问题标题】:find mean position and area of labelled objects找到标记对象的平均位置和面积
【发布时间】:2015-03-23 08:34:29
【问题描述】:

我有一个 2D 标记图像(numpy 数组),每个标签代表一个对象。我必须找到对象的中心及其区域。我目前的解决方案:

centers = [np.mean(np.where(label_2d == i),1) for i in range(1,num_obj+1)]

surface_area = np.array([np.sum(label_2d == i) for i in range(1,num_obj+1)])

请注意,用于中心的label_2d 与用于表面积的label_2d 不同,因此我不能将这两种操作结合​​起来。我当前的代码大约慢了 10-100 倍。

在 C++ 中,我将遍历图像一次(2 个 for 循环)并填充表格(一个数组),然后计算中心和表面积。

由于在 python 中 for 循环非常慢,我必须找到另一个解决方案。有什么建议吗?

【问题讨论】:

    标签: python image-processing numpy iteration labeling


    【解决方案1】:

    您可以将scipy.ndimage.measurements 中的center_of_mass function 用于第一个问题,然后将np.bincount 用于第二个问题。因为这些都在主流库中,所以它们会进行大量优化,因此您可以期待可观的速度提升。

    例子:

    >>> import numpy as np
    >>> from scipy.ndimage.measurements import center_of_mass
    >>> 
    >>> a = np.zeros((10,10), dtype=np.int)
    >>> # add some labels:
    ... a[3:5, 1:3] = 1
    >>> a[7:9, 0:3] = 2
    >>> a[5:6, 4:9] = 3
    >>> print(a)
    [[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 1 1 0 0 0 0 0 0 0]
     [0 1 1 0 0 0 0 0 0 0]
     [0 0 0 0 3 3 3 3 3 0]
     [0 0 0 0 0 0 0 0 0 0]
     [2 2 2 0 0 0 0 0 0 0]
     [2 2 2 0 0 0 0 0 0 0]
     [0 0 0 0 0 0 0 0 0 0]]
    >>> 
    >>> num_obj = 3
    >>> surface_areas = np.bincount(a.flat)[1:]
    >>> centers = center_of_mass(a, labels=a, index=range(1, num_obj+1))
    >>> print(surface_areas)
    [4 6 5]
    >>> print(centers)
    [(3.5, 1.5), (7.5, 1.0), (5.0, 6.0)]
    

    不过,速度提升取决于输入数据的大小,因此我无法对此做出任何认真的估计。如果您可以在 cmets 中添加该信息(a 的大小、标签数量、您使用的方法和这些函数的计时结果),那就太好了。

    【讨论】:

    • label_2d 的大小为 (2046,2046)。计时结果很大程度上取决于存在的对象数量:num_obj = 476, time = 6.88 sec; num_obj = 564,时间 = 8.11 秒; num_obj = 708,时间 = 10.23 秒; num_obj = 909, time = 13.20 sec 使用 2 个 for 循环(上述算法),执行时间约为 2.70 sec,与对象数量无关。
    • @soccersniper 您是在告诉我,您最初发布的代码始终比使用 bincountcenter_of_mass 两个预先编写的函数更快?
    • 所写的时间用于搜索中心。计算表面积需要更长的时间。
    • 不,写的时间是我以前的代码(来自问题)。
    • @soccersniper 很高兴听到这个消息,当你给出计时结果时我很困惑,不敢相信这是我提到的 2 个函数。
    猜你喜欢
    • 2022-06-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-11-07
    • 2017-09-29
    • 2013-11-09
    • 1970-01-01
    相关资源
    最近更新 更多