【问题标题】:To recognize curved line as a list将曲线识别为列表
【发布时间】:2016-02-17 08:15:02
【问题描述】:

我正在尝试从仅包含单个弯曲边缘的简单图像中识别曲线。 该线不能表示为公式,因为该线是完全随机生成的。 因此,保存曲线的唯一方法是保存像素位置并使用列表(或堆、向量等)连接它们。

例子:

噪声示例:

这个问题有什么算法或解决方案吗?

【问题讨论】:

  • 您需要在您的点上实现贝塞尔曲线拟合!更多细节在这里stackoverflow.com/questions/785097/… & 这里codeproject.com/Articles/25237/Bezier-Curves-Made-Simple
  • 我们可以举个例子吗?
  • 请发布一个示例图像,以及您目前尝试过的代码
  • 贝塞尔曲线拟合可能不是必需的,因为 OP 没有说他需要将曲线表示为贝塞尔曲线。可能是 OP 已经知道代表曲线的一组像素位置(不是按任何特定顺序),但只需要一种方法来找出它们的正确顺序。
  • 三木,我更新了我的问题,但我还没有实现代码。目前,我已经想到了算法,但有太多例外。我以为我可以通过查看相邻像素来知道方向,但很快我就意识到它可能会根据像素的位置而有所不同。

标签: list opencv image-processing line curve


【解决方案1】:

您可以使用findContoursdrawContours 执行此任务。这是tutorial from OpenCV

findContours 会将每个轮廓的有序点序列存储在std::vector<std::vector<cv::Point>> 中。您可以使用drawContour 重建原始轮廓。

或者您可以使用findNonZero 收集图像中的所有非零点,将点保存在std::vector<cv::Point> 中。然后,您可以设置所有这些点来重建您的原始图像。

看看下面代码中的两种方法:

#include <opencv2/opencv.hpp>
using namespace cv;

int main(int, char**)
{
    // Load grayscale image
    Mat1b img = imread("path_to_image", IMREAD_GRAYSCALE);

    // Get all contours in the image
    vector<vector<Point>> contours;
    findContours(img.clone(), contours, CV_RETR_LIST, CHAIN_APPROX_NONE);

    // Draw all contours in green on a black image
    Mat3b rec(img.rows, img.cols, Vec3b(0,0,0));
    drawContours(rec, contours, -1, Scalar(0,255,0), 1);

    imshow("Original", img);
    imshow("Reconstructed", rec);
    waitKey();


    // Save all non-zero pixel positions
    vector<Point> pts;
    findNonZero(img, pts);

    // Set the pixels to red, according to the points in pts
    Mat3b rec2(img.rows, img.cols, Vec3b(0, 0, 0));
    for (int i = 0; i < pts.size(); ++i)
    {
        rec2(pts[i]) = Vec3b(0,0,255);
    }

    imshow("Reconstructed 2", rec2);
    waitKey();

    return 0;
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-02-20
    相关资源
    最近更新 更多