0

我仍然是编码的初学者。我目前正在使用 C/C++ 编写一个程序,该程序正在确定照片中已定义标记(这是一个带有白色周围的黑色圆圈)的像素位置。
我从标记和一个向量制作了一个蒙版,其中包含蒙版的每个像素值作为它的元素(使用 Magick++ 我对红色、绿色和蓝色的值求和)。向量包含 aprox。10 000 个值,因为掩码为 100x100px。我还使用阈值函数来简化图像。

比我做了一个网格,也就是对图片做同样的事情,我想在其中找到标记的坐标。它基本上是一个循环,它遍历图像,当程序知道网格中的像素值时,它会立即将它们与掩码进行比较。主要思想是找到掩码和网格位置之一之间的最小差异。

然而,问题是评估所有网格位置的过程需要大量时间(例如,图像有 1920x1080 像素,因此超过 200 万个向量包含 10 000 个值)。我决定循环网格不是每个像素,而是例如每 10 列和行,并且为了从这个过程中获得最佳关联,我选择了使用每个像素循环的区域。但是,这仍然需要很多时间。

我想问你,是否有某种方法可以改进这种方法以获得更好(更快)的结果,或者整个想法不省时,我应该使用不同的方法。

感谢您的每一个建议!

编辑:该程序将用于处理多个图像,并且所有图像的大小都相同。这是阈值后的图片,标记是大黑点。 图片

4

2 回答 2

1

我觉得有趣的想法是金字塔方案 - 或渐进式细化:您在较小尺寸的图像中找到该点,然后在较大的图像中仅搜索一个小矩形。

如果您将图像在每个维度上减少 2,那么您会将时间减少 4 以及在较大图像中的一些搜索工作。

这有一些问题:减少会影响我期望的准确性。你可能会错过现场。

在这种情况下,您必须将样品(模板)切割成半尺寸模板。当你一半一半……模板会模糊到周围的物体中,所以不可能有一个有效的模板;一旦我猜到这个点周围有几个像素,就变成一半大小。

于 2016-04-03T16:40:39.957 回答
0

由于您没有指定工具或操作系统,我将选择安装在大多数 Linux 发行版上并且可用于 OSX 和 Windows 的 ImageMagick。我只是在命令行中使用它,但有可用的 C、C++、Python、Perl、PHP、Ruby、Java 和 .Net 绑定。

我会像这样使用“连接组件分析”“Blob 分析”

convert image.png -negate                            \
   -define connected-components:area-threshold=1200  \
   -define connected-components:verbose=true         \
   -connected-components 8 -auto-level result.png

我已经反转了您的图像,-negate因为在形态学操作中,前景通常是白色而不是黑色。我排除了小于 1200 像素的斑点,因为您的圆圈似乎有 22 像素的半径,这使得面积为 1520 像素 (Pi * 22^2)。

这给出了这个输出,这意味着 7 个 blob - 每行一个 - 具有边界框和每个区域的区域:

Objects (id: bounding-box centroid area mean-color):
  0: 1358x1032+0+0 640.8,517.0 1296947 gray(0)
  3: 341x350+1017+287 1206.5,468.9 90143 gray(255)
  106: 64x424+848+608 892.2,829.3 6854 gray(255)
  95: 38x101+44+565 61.5,619.1 2619 gray(255)
  49: 17x145+1341+379 1350.3,446.7 2063 gray(0)
  64: 43x43+843+443 864.2,464.1 1451 gray(255)
  86: 225x11+358+546 484.7,551.9 1379 gray(255)

请注意,由于您的圆圈是 42x42 像素,您将寻找一个方形且接近该大小的斑点 - 所以我正在查看倒数第二行。我可以在您的原始图像上用红色绘制,如下所示:

convert image.png -fill none -stroke red -draw "rectangle 843,443 886,486" result.png

在此处输入图像描述

另外,请注意,当您正在寻找一个圆圈时,您希望该区域为pi * r^21500 像素或大约 1500 像素,您可以在输出的倒数第二列中检查这一点。

在合理规格的 iMac 上运行 0.4 秒。请注意,您可以将图像分成 4 个并并行运行每个季度以加快速度。所以,如果你做这样的事情:

#!/bin/bash
# Split image into 4 (maybe should allow 23 pixels overlap)
convert image.png -crop 1x4@ tile-%02d.mpc

# Do Blob Analysis on 4 strips in parallel
for f in tile-*mpc; do
   convert $f -negate \
      -define connected-components:area-threshold=1200 \
      -define connected-components:verbose=true        \
      -connected-components 8 info: &
done
# Wait for all 4 to finish
wait

运行时间约为 0.14 秒。

于 2016-05-08T18:30:55.273 回答