图像处理:可口可乐罐识别算法改进

在过去的几年里,我参与的最有趣的项目之一是一个关于图像处理的项目。目标是开发一个能够识别可口可乐罐头的系统(请注意,我强调的是“罐”这个词,你很快就会明白为什么)。你可以在下面看到一个示例,通过比例和旋转在绿色矩形中识别罐子。

模板匹配

对项目的一些限制:

  • 背景可能非常嘈杂。
  • 可以可以有任何规模旋转甚至方向(在合理的范围内)。
  • 图像可能有一定程度的模糊性(轮廓可能不是完全直的)。
  • 图像中可能有可口可乐瓶,算法应该只检测可以
  • 图像的亮度可能会有很大的变化(所以你不能“太依赖”颜色检测)。
  • 可以可能部分隐藏在侧面或中间,也可能部分隐藏在瓶子后面。
  • 图像中可能根本没有可以,在这种情况下,您必须什么都找不到并写一条消息说明这一点。

所以你可能会遇到这样棘手的事情(在这种情况下,我的算法完全失败了):

总失败

我不久前做了这个项目,做起来很有趣,并且我有一个不错的实现。以下是我的实现的一些细节:

语言:C++使用OpenCV库完成。

预处理:对于图像预处理,即将图像转换为更原始的形式以提供给算法,我使用了2种方法:

  1. 将颜色域从RGB更改为HSV并根据“红色”色调进行过滤,饱和度超过某个阈值以避免类似橙色的颜色,并过滤低值以避免深色调。最终结果是二进制黑白图像,其中所有白色像素将代表与该阈值匹配的像素。显然图像中仍然有很多垃圾,但这减少了你必须处理的维度数量。二值化图像
  2. 噪声滤波使用中值滤波(取所有邻居的中值像素值并用此值替换像素)来降低噪声。
  3. 使用Canny边缘检测滤波器在2个先例步骤后获取所有项目的轮廓。轮廓检测

算法:我为这项任务选择的算法本身取自关于特征提取的第1本很棒的书,名为广义霍夫变换(与常规的霍夫变换非常不同)。它基本上说了一些事情:

  • 你可以在不知道其解析方程的情况下描述空间中的物体(这里就是这种情况)。
  • 它可以抵抗缩放和旋转等图像变形,因为它基本上会测试缩放因子和旋转因子的每个组合的图像。
  • 它使用算法将“学习”的基本模型(模板)。
  • 轮廓图像中剩余的每个像素将根据从模型中学到的内容投票给另一个像素,该像素应该是物体的中心(就重力而言)。

最后,你会得到一个投票的热图,例如,在这里,罐头轮廓的所有像素都将投票给它的引力中心,所以你会在对应于中心的同一个像素中有很多投票,并且会在热图中看到一个峰值,如下所示:

GHT

一旦你有了这个,一个简单的基于阈值的启发式可以给你中心像素的位置,从中你可以得出比例和旋转,然后在它周围绘制你的小矩形(最终的比例和旋转因子显然是相对于你的原始模板的)。

搜索结果:现在,虽然这种方法在基本情况下有效,但在某些领域严重缺乏:

  • 这是非常缓慢!我强调得不够。处理30张测试图像需要几乎一整天的时间,显然是因为我对旋转和平移的缩放系数非常高,因为有些罐子非常小。
  • 当瓶子在图像中时,它完全丢失了,出于某种原因,几乎总是找到瓶子而不是罐子(也许是因为瓶子更大,因此有更多的像素,因此更多的选票)
  • 模糊的图像也不好,因为投票最终在中心周围的随机位置以像素形式结束,从而以非常嘈杂的热图结束。
  • 实现了平移和旋转的方差,但在方向上没有,这意味着不能识别不直接面对相机物镜的罐子。

你能帮助我改进我的特定算法,使用独家OpenCV的功能,来解决上面提到的四个具体问题吗?

我希望有些人也能从中学到一些东西,毕竟我认为不仅仅是问问题的人应该学习。:)

229671 次浏览

如果您不仅限于不受限制的相机,也许您可以使用像XboxKinect这样的距离传感器。有了这个,您可以对图像执行基于深度和颜色的匹配分割。这可以更快地分离图像中的对象。然后,您可以使用ICP匹配或类似技术甚至匹配罐头的形状,而不仅仅是其轮廓或颜色,如果您之前对目标进行过3D扫描,这对于任何方向都是一个有效的选择。这些技术通常非常快,特别是用于这种特定目的时,应该可以解决您的速度问题。

我还建议,不一定是为了准确性或速度,而是为了好玩,你可以在你的色调分割图像上使用训练有素的神经网络来识别罐头的形状。这些非常快,通常可以达到80/90%的准确率。训练将是一个漫长的过程,尽管你必须手动识别每张图像中的罐头。

有趣的问题:当我看到你的瓶子图像时,我也以为它是一个罐头。但是,作为一个人,我所做的区分是,我随后注意到它也是一个瓶子…

所以,为了区分罐头和瓶子,先简单地扫描瓶子怎么样?如果你找到一个,在寻找罐头之前先把标签遮住。

如果你已经在做罐头,实施起来并不太难。真正的缺点是它会使你的流转时长翻倍。(但是考虑到现实世界的应用,你最终还是会想做瓶子;-)

这可能是一个非常天真的想法(或者可能根本不起作用),但是所有可乐罐的尺寸都是固定的。因此,如果同一图像同时包含罐头和瓶子,那么你可以通过尺寸考虑来区分它们(瓶子会更大)。现在,由于缺少深度(即3D映射到2D映射),瓶子可能看起来缩小了,并且没有大小差异。你可以使用立体成像恢复一些深度信息,然后恢复原始大小。

另一种方法是使用尺度不变特征变换(SIFT)或加速强大的功能(SURF)提取特征(关键点)。

您可以在此页面的JavaC++Python中找到一个不错的OpenCV代码示例:Features2D+寻找已知对象的单应性

这两种算法对于缩放和旋转都是不变的。由于它们适用于特征,你也可以处理遮挡(只要有足够的关键点可见)。

在此输入图片描述

图片来源:教程示例

SIFT处理需要几百毫秒,SURF快一点,但不适合实时应用。ORB使用FAST,旋转不变性较弱。

原始文件

我会检测红色矩形:RGB->HSV,过滤红色->二进制图像,关闭(扩张然后侵蚀,在matlab中称为imclose

然后从最大到最小查看矩形。在已知位置/比例中具有较小矩形的矩形都可以删除(假设瓶子比例不变,较小的矩形将是瓶盖)。

这会给你留下红色矩形,然后你需要以某种方式检测徽标来判断它们是红色矩形还是可乐罐。就像OCR一样,但有一个已知的徽标?

看形状

看看罐头/瓶子的红色部分的形状。注意罐头是如何在顶部稍微变细的,而瓶子标签是直的。你可以通过比较红色部分的宽度和长度来区分这两者。

看亮点

区分瓶子和罐头的一种方法是材料。瓶子是由塑料制成的,而罐头是由铝金属制成的。在光线充足的情况下,观察镜面是区分瓶子标签和罐头标签的一种方法。

据我所知,这是一个人分辨两种标签的方法。如果光照条件差,区分两者肯定会有一些不确定性。在这种情况下,你必须能够检测到透明/半透明瓶子本身的存在。

请看看Zdenek Kalal的捕食者追踪器。它需要一些训练,但它可以主动学习跟踪对象在不同方向和尺度下的外观,并实时完成!

源代码可以在他的网站上找到。它在MATLAB中,但也许社区成员已经完成了一个Java的实现。我在C#中成功地重新实现了TLD的跟踪器部分。如果我没记错的话,TLD使用蕨类作为关键点检测器。如果跟踪器丢失了对象,我使用SURF或SIFT(@stacker已经建议了)来重新获取对象。跟踪器的反馈使得随着时间的推移构建筛选/冲浪模板的动态列表变得容易,随着时间的推移,这些模板能够以非常高的精度重新获取对象。

如果您对我的跟踪器的C#实现感兴趣,请随时询问。

为了加快速度,我会利用这样一个事实,即你不需要找到任意的图像/对象,而是具体地找到带有可口可乐标志的图像/对象。这很重要,因为这个标志非常独特,它应该在频域中具有特征性、比例不变的特征,特别是在RGB的红色通道中。也就是说,水平扫描线(在水平对齐的标志上训练)遇到的红色到白色到红色的交替图案在穿过标志的中轴时将具有独特的“节奏”。这种节奏将在不同的尺度和方向上“加速”或“减速”,但仍将保持比例等效。你可以在星爆图案中识别/定义几十条这样的扫描线,水平和垂直穿过徽标,还有更多的对角线。称之为“签名扫描线”。

签名扫描线

在目标图像中搜索此特征很简单,只需将图像扫描成水平条带。在红色通道中寻找高频(表示从红色区域移动到白色区域),一旦找到,看看它是否跟着训练会话中识别的频率节奏之一。一旦找到匹配,你将立即知道扫描线在徽标中的方向和位置(如果你在训练中跟踪这些事情),因此从那里识别徽标的边界是微不足道的。

如果这不是一个线性有效的算法,或者几乎是这样,我会感到惊讶。它显然不能解决你对罐装瓶的歧视,但至少你会有你的标志。

(更新:对于瓶子识别,我会寻找与徽标相邻的可乐(棕色液体)-也就是说,瓶子里面。或者,对于空瓶子,我会寻找一个,它将始终具有相同的基本形状,大小和与徽标的距离,并且通常都是白色或红色。搜索一个纯色椭圆形状,其中帽应该相对于徽标。当然不是万无一失的,但您的目标应该是找到容易快速。)

(我的图像处理时代已经过去几年了,所以我把这个建议保持在高层次和概念性的。我认为它可能会稍微近似于人眼的运作方式-或者至少我的大脑是如何运作的!)

在第二张图片中,人类是否很难区分瓶子和罐头(前提是瓶子的透明区域是隐藏的)?

它们几乎是相同的,除了一个非常小的区域(即,在顶部的宽度可以是有点小,而瓶子的包装是相同的宽度在整个,但一个微小的变化对吗?)

我想到的第一件事是检查瓶子的红色顶部。但是,如果瓶子没有顶部,或者它被部分隐藏(如上所述),这仍然是一个问题。

我想到的第二件事是关于瓶子的透明度。OpenCV有一些在图像中查找透明物体的工作。查看下面的链接。

特别看看这个,看看他们检测玻璃的准确性:

查看其实施结果:

在此处输入图像描述

他们说这是文件“用于寻找玻璃的测地线活动轮廓框架”,K. McHenry和J. Ponce,CVPR 2006的实现。

这可能对你的情况有点帮助,但问题再次出现,如果瓶子装满了。

所以我认为在这里,你可以先搜索瓶子的透明主体,或者搜索一个连接到两个透明物体的红色区域,这显然是瓶子。(理想情况下,图像如下。)

在此处输入图像描述

现在你可以删除黄色区域,即瓶子的标签,并运行你的算法来找到罐头。

无论如何,这个解决方案也像其他解决方案一样存在不同的问题。

  1. 只有当你的瓶子是空的时,它才起作用。在这种情况下,你必须搜索两种黑色之间的红色区域(如果可口可乐液体是黑色的)。
  2. 另一个问题是透明部分是否被覆盖。

但无论如何,如果图片中没有上述问题,这似乎是一个更好的方法。

我不知道OpenCV,但从逻辑上看待这个问题,我认为你可以通过改变你正在寻找的图像来区分瓶子和罐子,即可口可乐。你应该把罐子的顶部加入,因为在罐子的情况下,可口可乐的顶部有一线希望,在瓶子的情况下,没有这样的一线希望。

但显然,这种算法在罐头顶部隐藏的情况下会失败,但在这种情况下,即使是人类也无法区分两者(如果只有可口可乐部分的瓶子/罐头可见)

我真的很喜欢这个问题的0和1。我正在把我的想法投入到对这些问题的评论中,但我相信我的方法太答案形了,不能离开这里。

简而言之,你已经确定了一种算法来确定可口可乐徽标是否存在于空间中的特定位置。你现在正试图确定,对于任意方向和任意缩放因子,一种启发式方法,适用于将可口可乐与其他物体区分开来,包括:广告牌广告可口可乐用具,它们都与这个标志性徽标相关。你在问题陈述中没有指出许多这些额外的情况,但我觉得它们对你算法的成功至关重要。

这里的秘诀是确定可以包含哪些视觉特征,或者通过负空间确定罐头中不存在的其他可口可乐产品存在哪些特征。为此,当前最高答案勾勒出了一种选择“罐”的基本方法,当且仅当“瓶子”没有被识别时,无论是瓶盖、液体还是其他类似的视觉启发式。

问题是这会崩溃。例如,一个瓶子可能是空的,没有盖子,导致误报。或者,它可能是半瓶,附加功能被破坏,再次导致错误检测。不用说,这不是优雅的,对我们的目的也不有效。

为此,罐头最正确的选择标准似乎如下:

  • 对象轮廓的形状,如你在问题中勾勒出的,正确吗?如果是,+1。
  • 如果我们假设存在自然光或人造光,我们是否检测到瓶子的铬轮廓,表明它是否由铝制成?如果是,+1。
  • 相对于我们的光源(说明性视频链接光源检测),我们是否确定对象的镜面特性是正确的?如果是,+1。
  • 我们是否可以确定有关对象的任何其他属性,以将其识别为罐头,包括但不限于徽标的拓扑图像倾斜,对象的方向,对象的并置(例如,在像桌子这样的平面表面上或在其他罐头的上下文中),以及拉片的存在?如果是这样,对于每个,+1。

您的分类可能如下所示:

  • 对于每个候选匹配,如果检测到可口可乐徽标的存在,则绘制灰色边框。
  • 对于超过+2的每个匹配,绘制红色边框。

这在视觉上向用户突出显示了检测到的内容,强调了可能被正确检测为损坏的罐头的弱阳性。

对每个属性的检测都有非常不同的时间和空间复杂度,对于每种方法,快速浏览http://dsp.stackexchange.com对于确定最正确和最有效的算法来说是非常合理的。我在这里的意图纯粹而简单地强调通过使候选检测空间的一小部分无效来检测某物是否是罐不是这个问题的最健壮或最有效的解决方案,理想情况下,你应该采取相应的行动。

嘿,恭喜黑客新闻发布!总的来说,这是一个非常棒的问题,值得它所收到的宣传。:)

有一堆颜色描述符用于识别对象,下面的论文比较了很多。当它们与SIFT或SURF结合使用时,它们特别强大。单独使用SURF或SIFT在可口可乐罐图像中不是很有用,因为它们不能识别很多兴趣点,你需要颜色信息来帮助。我在一个项目中使用BIC(边界/内部像素分类)和SURF,它在识别对象方面非常有效。

用于Web图像检索的颜色描述符:比较研究

我喜欢你的问题,不管是否跑题: P

有趣的是,我刚刚完成了我的学位课程,其中包括机器人和计算机视觉。我们这学期的项目和你描述的非常相似。

我们必须开发一个机器人,它使用Xbox Kinect在各种照明和环境条件下以任何方向检测可乐瓶和罐头。我们的解决方案涉及在色调通道上使用带通滤波器并结合霍夫圆变换。我们能够对环境进行一点约束(我们可以选择机器人和Kinect传感器的位置和方式),否则我们将使用SIFT或SURF变换。

您可以在我关于这个主题的博客文章上阅读我们的方法:)

我喜欢这个挑战,并想给出一个答案,我认为这解决了这个问题。

  1. 提取徽标的特征(关键点,描述符,如SIFT,SURF)
  2. 将点与徽标的模型图像匹配(使用Matcher,例如Brute Force)
  3. 估计刚体的坐标(PnP问题-SolvePnP)
  4. 根据刚体估计盖帽位置
  5. 做反投影并计算瓶盖的图像像素位置(ROI)(我假设你有相机的内在参数)
  6. 用方法检查盖子是否在那里。如果有,那么这就是瓶子

上限的检测是另一个问题。它可以是复杂的,也可以是简单的。如果我是你,我会简单地检查ROI中的颜色直方图来做一个简单的决定。

如果我错了,请反馈。谢谢。

有一个来自MVTec的名为HALCON的计算机视觉包,其演示可以为您提供很好的算法想法。您可以在演示模式下运行大量类似于您的问题的示例,然后查看代码中的运算符,并了解如何从现有的OpenCV运算符中实现它们。

我用这个包来快速地为这样的问题制作复杂算法的原型,然后找到如何使用现有的OpenCV特性来实现它们。特别是对于你的情况,你可以尝试在OpenCV中实现嵌入在操作符find_scaled_shape_model中的功能。一些操作符指向关于算法实现的科学论文,这有助于找出如何在OpenCV中做类似的事情。

嗯,我实际上认为我在东西(这是有史以来最有趣的问题——所以不继续寻找“完美”的答案是一种耻辱,即使已经找到了一个可以接受的答案)…

一旦你找到了标志,你的麻烦就完成了一半。然后你只需要弄清楚标志周围之间的区别。此外,我们希望尽可能少地做额外的事情。我认为这实际上是这个简单的部分…

标志周围的是什么?对于罐头,我们可以看到金属,尽管受到灯光的影响,但其基本颜色不会发生任何变化。只要我们知道标签的角度,我们就可以分辨出它的正上方是什么,所以我们正在查看它们之间的区别:

在这里,标志的上方和下方是完全黑暗的,颜色一致。在这方面相对容易。

在这里,上面和下面的是光,但颜色仍然一致。它是全银色的,全银色金属实际上看起来很罕见,以及一般的银色。此外,它在一个薄的滑块中,并且足够接近已经确定的红色,因此您可以追踪其整个长度的形状,以计算出可以被认为是罐子金属环的百分比。真的,你只需要沿着罐子的任何地方的一小部分,就可以告诉它它是它的一部分,但你仍然需要找到一个平衡,以确保它不仅仅是一个背后有金属的空瓶子。

最后,棘手的一个。但不是那么棘手,一旦我们只通过我们可以看到的红色包装纸的正上方(和下方)。它是透明的,这意味着它会显示它背后的任何东西。这很好,因为它后面的东西不太可能像罐子的银色圆形金属一样颜色一致。它后面可能有许多不同的东西,这会告诉我们它是一个空的(或装满了透明液体)瓶子,或者是一个一致的颜色,这可能意味着它装满了液体,或者瓶子只是在一个纯色的前面。我们正在使用最接近顶部和底部的东西,正确的颜色出现在正确位置的机会相对较小。我们知道这是一个瓶子,因为它没有罐头的关键视觉元素,这与瓶子后面的东西相比相对简单。

(最后一个是我能找到的最好的一个空的大可口可乐瓶——有趣的是,瓶盖和戒指是黄色的,表明瓶盖的红色可能不应该被依赖)

在极少数情况下,即使在抽象塑料之后,瓶子后面也有类似的银色阴影,或者瓶子以某种方式充满了相同的银色液体,我们可以依靠我们可以粗略估计的银的形状——正如我所说,银是圆形的,遵循罐子的形状。但即使我缺乏图像处理方面的某些知识,这听起来也很慢。更好的是,为什么不通过检查标志的双方来推断这一点,以确保那里没有相同的银色?啊,但是如果罐子后面有相同的银色呢?然后,我们确实必须更加注意形状,再次查看罐头的顶部和底部。

根据这一切需要有多完美,它可能会非常慢,但我想我的基本概念是首先检查最简单和最接近的东西。在计算其他元素的形状之前,先通过已经匹配的形状周围的颜色差异(无论如何,这似乎是最琐碎的部分)。为了列出它,它是:

  • 找到主要的吸引力(红色的标志背景,可能是标志本身的方向,但如果可以转身离开,你需要专注于红色)
  • 验证形状和方向,再次通过非常独特的红色
  • 检查形状周围的颜色(因为它快速无痛)
  • 最后,如果需要,验证主要吸引力周围的颜色的形状,以获得正确的圆度。

如果你不能这样做,这可能意味着罐头的顶部和底部都被覆盖了,人类唯一可以用来可靠地区分罐头和瓶子的东西就是罐头的遮挡和反射,这将是一场更难处理的战斗。然而,更进一步,你可以使用其他答案中提到的半透明扫描技术,沿着罐头/瓶子的角度检查更多类似瓶子的特征。

有趣的额外噩梦可能包括一个易拉罐方便地坐在瓶子后面,距离如此之远,以至于它的金属恰好显示在标签的上方和下方,只要你沿着红色标签的整个长度扫描,它仍然会失败——这实际上是一个更大的问题,因为你没有检测到一个可以有的罐子,而不是考虑到你实际上是在检测一个瓶子,包括罐子。在这种情况下,玻璃杯是半空的!


作为免责声明,在这个问题之外,我没有经验,也从来没有想过图像处理,但它是如此有趣,它让我深入思考,在阅读了所有其他答案后,我认为这可能是最简单的最有效的方法来完成它。就个人而言,我很高兴我不必考虑编程这个!

编辑

MS油漆中罐头的糟糕绘图此外,看看这幅画我在MS油漆…这绝对是可怕的,相当不完整的,但仅根据形状和颜色,你可以猜测它可能是什么。本质上,这些是唯一需要扫描的东西。当你看到非常独特的形状和颜色组合如此接近时,它还可能是什么?我没有画的那一点,白色背景,应该被认为是“任何不一致的东西”。如果它有一个透明的背景,它几乎可以覆盖任何其他图像,你仍然可以看到它。

作为所有这些不错的解决方案的替代方案,您可以训练自己的分类器并使您的应用程序对错误具有鲁棒性。例如,您可以使用Haar培训,提供目标的大量正面和负面图像。

仅提取罐头可能很有用,并且可以与透明物体的检测相结合。

深度学习

收集至少几百个包含可乐罐的图像,将它们周围的边界框注释为正类,包括可乐瓶和其他可乐产品,将它们标记为负类以及随机对象。

除非您收集非常大的数据集,否则请对小数据集使用深度学习特征。理想情况下使用支持向量机(SVM)与深度神经网络的组合。

一旦您将图像提供给先前训练的深度学习模型(例如GoogleNet),而不是使用神经网络的决策(最终)层进行分类,而是使用先前层的数据作为特征来训练您的分类器。

OpenCV和Google Net:http://docs.opencv.org/trunk/d5/de7/tutorial_dnn_googlenet.html

OpenCV和SVM:http://docs.opencv.org/2.4/doc/tutorials/ml/introduction_to_svm/introduction_to_svm.html

如果你对实时感兴趣,那么你需要的是添加一个预处理过滤器来确定用重型材料扫描什么。一个快速、非常实时的预处理过滤器,它将允许你扫描更有可能是可口可乐罐的东西,然后再转移到更不确定的东西上,就像这样:在图像中搜索最大的颜色补丁,这些颜色距离可口可乐罐的sqrt(pow(red,2) + pow(blue,2) + pow(green,2))有一定的容忍度。从非常严格的颜色容忍度开始,然后逐步降低到更宽松的颜色容忍度。然后,当您的机器人用完分配的时间来处理当前帧时,它会将当前找到的瓶子用于您的目的。请注意,您必须调整sqrt(pow(red,2) + pow(blue,2) + pow(green,2))中的RGB颜色以使它们恰到好处。

此外,这看起来很愚蠢,但您在编译C代码时是否确保打开-oFast编译器优化?

我首先要寻找的是颜色-就像RED一样,当在图像中进行红眼检测时-有一定的颜色范围需要检测,考虑到周围区域的一些特征,例如与另一只眼睛的距离,如果它确实在图像中可见。

1:第一个特征是颜色,红色非常占主导地位。检测到可口可乐红色后,有几个感兴趣的项目1A:这个红色区域有多大(它的数量是否足以确定真正的罐头-10个像素可能不够),1B:它是否包含标签的颜色-“可口可乐”或波浪。1B1:是否有足够的概率认为它是一个标签。

第1项是一种捷径-如果图像中不存在该doe,则进行预处理-继续前进。

因此,如果是这种情况,我可以利用我的图像的该片段并开始更多地缩小所讨论的区域-基本上是查看周围的区域/边缘……

2:给定上述图像区域ID'd在1-验证有问题的项目的周围点[边缘]。A:有没有看起来像罐头顶部或底部的东西——银色的?B:一个瓶子看起来可能是透明的,但是一个玻璃桌子也可能是透明的——那么是否有一个玻璃桌子/架子或一个透明的区域——如果是这样,就有多种可能。一个瓶子可能有一个红色的盖子,也可能没有,但它应该有瓶盖/螺纹螺丝的形状,或者一个盖子。C:即使A和B失败了,它仍然可以是部分的。这是更复杂的,当它是部分,因为部分瓶/部分可以看起来一样,所以一些更多的处理测量的红色区域边缘到边缘…

3:在上面的分析之后,当我看到字母和波浪标志时-因为我可以定位我在单词中搜索的一些字母,因为你可能没有所有的文本,因为没有所有的可以,波浪会在某些点对齐文本(距离明智),所以我可以搜索概率,知道哪些字母应该存在于距离x的波浪的那个点。

您需要一个从经验中有机地学习和提高分类准确性的程序。

我建议深度学习,有了深度学习,这就变成了一个微不足道的问题。

您可以在Tensorflow上重新训练inception v3模型:

如何为新类别重新训练初始的最终层

在这种情况下,你将训练一个卷积神经网络来将一个物体分类为可口可乐罐或不罐。

也许晚了很多年,但仍然有一个理论可以尝试。

红色标志区域的边框与瓶子/罐头的整体尺寸的比例不同。在Can的情况下,应该是1:1,而在瓶子(带或不带盖)的情况下会有所不同。这样就很容易区分两者了

更新:由于罐头和瓶子各自的尺寸差异,徽标区域的水平曲率在罐头和瓶子之间会有所不同。如果您的机器人需要拿起罐头/瓶子,并且您相应地决定握把,这可能特别有用。

我在回答这个问题上晚了几年。在过去的5年里,CNN将最先进的技术推向了极限,我现在不会用OpenCV来完成这项任务!(我知道你在问题中特别想要OpenCv功能)我觉得目标检测算法,如Faster-RCNN、活在当下、SSD等,与OpenCV功能相比,会在很大程度上解决这个问题。如果我现在解决这个问题(6年后!!)我肯定会使用Faster-RCNN