选择更大的球

时间:2012-03-27 15:35:58

标签: python algorithm image image-processing

我有一系列数据填充“#”和“。”例如,它显示如下:

...........#############..............................
.........################..................#######....
........##################................#########...
.......####################..............###########..
........##################................#########...
.........################..................#######....
...........#############..............................

我想创建一个算法,找到更大的球并擦除较小的球。 我想用最长的“#”序列来知道直径是多少。

所以我有这样的事情:

x = 0
longest_line = 0
for i in range(0, nbLine) :
   for j in range(0, nbRaw) :
       if data[i, j] = red :
          x = x+1
          if data[i, j+1] != red: 

我不知道下一步该做什么..

4 个答案:

答案 0 :(得分:3)

我会使用某种segmentation algorithm,然后简单地计算每个对象中的像素数。然后简单地擦除较小的一个,这应该很容易,因为你有一个对象的标签。

分段算法通常可以这样工作。

  1. 执行光栅扫描,从左上角开始,向右下方工作。
  2. 当你看到一个#时,你知道你有一个对象。检查它的邻居。
  3. 如果邻居具有先前分配的值,则将该值分配给它
  4. 如果有多个值,请将其放入某种表中,在完成处理后,您将进行简化。
  5. 所以,举个简单的例子:

    ...##...
    .######.
    ...##...
    

    您的处理将如下所示:

    00011000
    02111110
    00011000
    

    通过以下转换: 2 =大于1

    应用查找表,所有对象都将标记为1值。然后只需计算像素数,就完成了。

    我会把实施留给你; - )

答案 1 :(得分:2)

  1. 将您的数据转换为更好的数组结构
  2. 执行connected component labelling
  3. 计算每个标签的元素数量(忽略背景标签)
  4. 选择元素数量最多的标签

答案 2 :(得分:2)

你是否只有2个像这样的形状?因为在这种情况下,您还可以使用python正则表达式库。这段代码似乎为你的例子做了伎俩(我把你的小图画复制到一个文件中并命名为“balls.txt”):

import re

f = open("balls.txt", "r")

for line in f :

   balls = re.search("(\.+)(#+)(\.+)(#*)(\.+)", line) 

   dots1 = balls.groups()[0]
   ball1 = balls.groups()[1]
   dots2 = balls.groups()[2]
   ball2 = balls.groups()[3]
   dots3 = balls.groups()[4]

   if len(ball1) < len(ball2): 
       ball1 = ball1.replace('#', '.')
   else:
       ball2 = ball2.replace('#', '.')

   print "%s%s%s%s%s" % (dots1, ball1, dots2, ball2, dots3)

这就是我得到的:

...........#############..............................
.........################.............................
........##################............................
.......####################...........................
........##################............................
.........################.............................
...........#############..............................

我希望这可以为您解决问题提供一些想法

答案 3 :(得分:0)

假设球不接触:

假设正好两个球

创建两个球对象(称为球0和1),每个球对象拥有一组点。点是x,y对。

在每行内从上到下,从左到右扫描每一行。

当你看到第一个#时,将它分配给球0(将它的x,y线加到球0对象拥有的集合中)。

当你看到任何后续的#时,如果它与球0中已经存在的任何点相邻,则将其添加到球0;否则将它添加到球1.(如果新的#在x,y我们只测试(x + 1,y)在集合中,(x-1,y)在集合中,(x,y + 1)是在集合中,(x,y-1)在集合中,而对角线邻居在其中)

扫描完成后,列表大小显示较大的球。然后,您可以在其他球的点数集中列出要删除的点数。