1

我尝试实现名为OpenCV 2 Computer Vision Application Programming Cookbook的书中的示例,该书显示了如何在 Hough Probabilistic Algorithm 的帮助下找到一条线(第 170 页)。(顺便说一句,一本非常好的书!) pdf格式的书

但是我在使用 C++ 时遇到了一些问题,我不是编程专家,为什么我需要你的帮助。Visual Studio 向我显示以下错误:

LineTracking_v02.exe 中 0x00e274b7 处的未处理异常:0xC0000005:访问冲突读取位置 0x00000000。

当我调试时,它似乎来自第 57 行('return lines;' in 'findLines' function)。

你知道为什么吗?

这是我的代码:

//v2

#include "opencv\cv.h"
#include "opencv\highgui.h"
#include <iostream>
using namespace cv;
using namespace std;
#define PI 3.1415926535898


class LineFinder{
private :
    //original image
    cv::Mat img;
    //vector containing the end points of the detected lines
    std::vector<cv::Vec4i> lines;
    //accumulator resolution parameters
    double deltaRho;
    double deltaTheta;
    //minimum number of votes that a lines must receive before
    //being considered
    int minVote;
    //min length for a line
    double minLength;
    //max allowed gap along the line
    double maxGap;

public:
    //default accumulator resolution is 1 pixel by 1 degree,
    //no gap, no minimum length
    LineFinder() :  deltaRho(1), 
        deltaTheta(PI/180), 
        minVote(10),
        minLength(0.) {}

    //Set the resolution of the accumulator
    void setAccResolution(double dRho, double dTheta){
        deltaRho = dRho;
        deltaTheta = dTheta;
    }

    //Set the minimum number of votes
    void setMinVote(int minv){
        minVote = minv;
    }

    //Set line length and gap
    void setLineLengthAndGap(double length, double gap){
        minLength = length;
        maxGap = gap;
    }

    //Apply probabilistic Hough Transform
    std::vector<cv::Vec4i> findLines(cv::Mat& binary){
        lines.clear();
        cv::HoughLinesP(binary, lines, deltaRho, deltaTheta, minVote, minLength, maxGap);
        return lines;
    }

    //Draw the detected lines on an image
    void drawDetectedLines(cv::Mat &image, cv::Scalar color=cv::Scalar(255,255,255)){
        std::vector<cv::Vec4i>::const_iterator it2 = lines.begin();
        while(it2!=lines.end()){
            cv::Point pt1((*it2)[0], (*it2)[1]);
            cv::Point pt2((*it2)[2], (*it2)[3]);
            cv::line(image, pt1, pt2, color);
            ++it2;
        }
    }
};

int main(int, char**)
{
    // Open the default camera
    cv::VideoCapture capture(0); 
    // Check if we succeeded
    if(!capture.isOpened()) 
    {
        std::cout<<"Video capture failed, please check the camera."<<std::endl;
        return -1;
    }else{
        std::cout<<"Video camera capture successful!"<<std::endl;
    }

    for(;;) {
        cv::Mat frame;
        cv::Mat grayFrame;
        cv::Mat gaussGrayFrame;
        cv::Mat edges;
        LineFinder finder;

        capture >> frame; // get a new frame from camera

        //Convert the frame into a gray Frame
        cv::cvtColor(frame, grayFrame, CV_BGR2GRAY);

        //Apply a Gaussian Blur on the gray-level Frame
        cv::GaussianBlur(grayFrame, gaussGrayFrame, cv::Size(7,7), 1.5, 1.5);

        //Apply Canny Algorithm
        cv::Canny(
            gaussGrayFrame, // gray-level source image
            edges,          // output contours
            0,              // low threshold
            30,             // high threshold
            3);             // aperture size
        //End Canny Algorithm

        //Detect lines
        std::vector<cv::Vec4i> lines = finder.findLines(edges);
        //Draw the detected lines
        finder.drawDetectedLines(frame);

        cv::imshow("Camera Preview", frame);
        if(cv::waitKey(30) >= 0) break;
    }

    // the camera will be deinitialized automatically in VideoCapture destructor
    return 0;
}

提前感谢您的帮助!

4

2 回答 2

2

我刚刚在 Ubuntu Linux 下成功编译并执行了你的程序。我目前的随机理论是edges在您的环境中没有正确初始化。

我会插入一些cv::imwritecv::imshow(对于 frame、grayFrame、edges)来查看是否所有图像都包含合理的值。

于 2012-04-19T11:03:12.770 回答
1

所以你会继续前进而不确定失败吗?它肯定会回来咬你。

我的猜测:你什么都不做来检查框架是否真的被读取了,这会搞砸一些事情,我的猜测是:当你去在一个不存在的图像中绘制随机的东西时。

于 2013-06-20T06:46:28.103 回答