3

我使用 SIFT 进行特征检测,使用 calcOpticalFlowPyrLK 进行图像中的特征跟踪。我正在处理从 Microsoft kinect 拍摄的低分辨率图像(裁剪后为 590x375)。

// feature detection
cv::Ptr<Feature2D> detector = cv::xfeatures2d::SIFT::create();
detector->detect(img_1,keypoints_1);
KeyPoint::convert(keypoints_1, points1, vector<int>());

// feature tracking
vector<float> err;
Size winSize=Size(21,21);
TermCriteria termcrit=TermCriteria(TermCriteria::COUNT+TermCriteria::EPS, 30, 0.01);
calcOpticalFlowPyrLK(img_1, img_2, points1, points2, status, err, winSize, 1, termcrit, 0, 0.001);

我在同一相机位置以 30fps 的速度拍摄的稳定场景的连续图像(只是为了了解一下)上运行了这个。对眼睛来说,图像看起来是一样的,但不知何故 calcOpticalFlowPyrLK 无法跟踪从一张图像到另一张图像的相同特征。检测到的特征和跟踪的特征中的位置(x,y 坐标)应该相同。不知何故不是。

根据 AldurDisciple 的建议,我认为我将噪声检测为特征。下面的黑色图像是导电元素之间的差异,显示了噪声。接下来是原始图像,然后是具有检测到的特征的图像。

我的目标是使用信息来发现机器人位置随时间的变化。

我用了

GaussianBlur( currImageDepth, currImageDepth, Size(9,9), 0, 0); 

噪音,但它没有帮助。

在这里找到完整的代码 在此处输入图像描述

在此处输入图像描述

在此处输入图像描述

在此处输入图像描述

在此处输入图像描述

在此处输入图像描述

4

1 回答 1

3

我认为你应该考虑两个因素:

  1. 您的场景基本上由 3 个同质区域组成,因此这些区域中的 FAST 点很可能是由图像中的噪声产生的。由于两个连续图像中的噪声模式可能完全不同,因此某些点的最佳匹配可能位于图像中完全不同的位置。

  2. 您的图像已经具有相当低的分辨率,并且函数3的参数列表中的calcOpticalFlowPyrLK意味着您需要该函数使用 4 级金字塔来跟踪点。这意味着点将首先在调整大小为 2^3 = 16 的图像(即 ~ 36x23 图像)中跟踪,然后在调整大小为 2^2 = 8 的图像(即 ~ 73x46 图像)中进行跟踪,依此类推. 36x23 的初始分辨率对于几乎没有纹理的图像来说太低了。

为了解决您的问题,您可以尝试仅使用两个金字塔级别(即通过1而不是3),甚至是一个级别(即通过0而不是3)。但请记住,噪音问题意味着通常您总会遇到一些错误匹配。

另一方面,在没有相机运动的静态场景中跟踪点似乎是一个人为的问题。在实际场景中,您可能对使用移动摄像机跟踪场景或静态场景中的运动更感兴趣,在这种情况下,使用多个金字塔级别会很有用。

于 2016-11-05T14:30:32.817 回答