我目前正在研究一个基于视频监控的入侵系统。为了完成这项任务,我拍摄了场景背景的快照(假设它是完全干净的,没有人或移动的物体)。然后,我比较我从(静态)摄像机得到的帧,寻找差异。我必须能够检查任何的差异,不仅是人类的形状或任何东西,所以我不能具体的特征提取。
通常,我有:
我正在使用OpenCV,所以为了比较我基本上是这样做的:
cv::Mat bg_frame;
cv::Mat cam_frame;
cv::Mat motion;
cv::absdiff(bg_frame, cam_frame, motion);
cv::threshold(motion, motion, 80, 255, cv::THRESH_BINARY);
cv::erode(motion, motion, cv::getStructuringElement(cv::MORPH_RECT, cv::Size(3,3)));
结果如下:
正如你所看到的,手臂被剥离(由于色差冲突我猜),可悲的是这不是我想要的。
我考虑过添加cv::Canny()
的使用,以便检测边缘并填充手臂的缺失部分,但遗憾的是(再次),它只在少数情况下解决了问题,而不是大多数情况。
是否有任何算法或技术可以用来获得一个 * 准确 * 的差异报告?
PS:对不起图片。由于我是新订阅的,我没有足够的声誉。
编辑我在这里使用灰度图像,但我愿意接受任何解决方案。
4条答案
按热度按时间afdcj2ne1#
代码中的一个问题是
cv::threshold
,它只使用1个通道图像。仅在灰度中找到两个图像之间的逐像素“差异”通常导致不直观的结果。由于您提供的图像有点平移或者相机不是固定的,我已经操作了背景图像以添加一些前景:
背景图像:
前景图像:
代码:
给出这个结果:
用这个差分图像:
通常,难以根据逐像素差异解释来计算完整前景/背景分割。
您可能需要添加后处理的东西,以获得一个真实的的分割,在那里你从你的前景蒙板开始。不确定是否有任何稳定的通用解决方案。
正如berak提到的,实际上使用一个背景图像是不够的,所以你必须随着时间的推移计算/管理你的背景图像。有大量的论文涉及这个主题,但目前还没有稳定的通用解决方案。
这里还有一些测试。转换为
HSV
颜色空间:cv::cvtColor(backgroundImage, HSVbackgroundImagebg, CV_BGR2HSV); cv::cvtColor(currentImage, HSV_currentImage, CV_BGR2HSV);
并在此空间中执行相同的操作,导致以下结果:在输入端添加一些噪声后:
我得到这个结果:
所以门槛可能有点太高了我仍然鼓励你看看HSV颜色空间太多,但你可能需要重新解释“差异图像”并重新缩放每个通道以合并它们的差异值。
tp5buhyn2#
我使用Python,这是我的结果:
代码:
更新,这里是C++代码:
类似的答案:
1.当发现两张图片之间的差异OpenCV差异大于预期
cig3rfwq3#
另一种获得两幅图像之间精确像素差异的技术是使用在论文Image Quality Assessment: From Error Visibility to Structural Similarity中首次引入的结构相似性指数(SSIM)。该方法可以用于确定两个图像是否相同和/或由于微小的图像差异而展示差异。SSIM已在scikit-image library中实现,用于图像处理,如
skimage.metrics.structural_similarity()
structural_similarity()
函数返回一个score
和一个差值图像diff
。score
表示两个输入图像之间的平均结构相似性指数,并且可以落在范围[-1,1]
之间,其中越接近1的值表示越高的相似性。但是,由于您只对这两个图像的不同之处感兴趣,因此我们将重点关注diff
图像。具体地,diff
图像包含实际图像差异,其中较暗区域具有较大的视差。较大的差异区域以黑色突出显示,而较小的差异以灰色突出显示。使用这两个输入图像
我们得到这个结果
对比两张图片后的SSIM评分显示,它们非常相似
图像相似度:95.8648%
vatpfxk54#
这是一个著名的经典计算机视觉问题,叫做背景减除。有很多方法可以用来解决这个问题,其中大部分已经实现,所以我认为你应该先看看现有的多种算法,这里是其中大部分的开源实现:https://github.com/andrewssobral/bgslibrary(我个人发现SUBSENSE的效果最好,但它的速度非常慢)