简体   繁体   English

使用C ++的SVM教程

[英]Tutorials for SVM with c++

I am trying to use SVM for object detection with c++. 我正在尝试使用SVM使用c ++进行对象检测。 I am following this answer . 我正在关注这个答案 I am facing one problem that CvSVM is not used as of now. 我面临的一个问题是,到目前为止,尚未使用CvSVM。 So I have modified the training code as follows. 因此,我对培训代码进行了如下修改。

#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/ml/ml.hpp>

using namespace cv;
using namespace cv::ml;

int main()
{
    // Data for visual representation
        int width = 512, height = 512;
    Mat image = Mat::zeros(height, width, CV_8UC3); 

    // Set up training data
        float labels[4] = {1.0, -1.0, -1.0, -1.0};
        Mat labelsMat(4, 1, CV_32FC1, labels);  
    float trainingData[4][2] = { {501, 10}, {255, 10}, {501, 255}, {10, 501} };
    Mat trainingDataMat(4, 2, CV_32FC1, trainingData);

// Set up SVM's parameters
        Ptr<SVM> svm = SVM::create();
        svm->setType(SVM::C_SVC);
        svm->setKernel(SVM::LINEAR);
//svm.term_crit   = SVM::getTermCriteria(CV_TERMCRIT_ITER, 100, 1e-6);

// Train the SVM
//Ptr<SVM> svm1 = SVM::trainAuto();

        SVM->train(trainingDataMat, labelsMat, Mat(), Mat(), svm);

        Vec3b green(0,255,0), blue (255,0,0);
// Show the decision regions given by the SVM
        for (int i = 0; i < image.rows; ++i)
        for (int j = 0; j < image.cols; ++j)
        {
                Mat sampleMat = (Mat_<float>(1,2) << j,i);
                float response = svm->predict(sampleMat);

                if (response == 1)
                image.at<Vec3b>(i,j)  = green;
                else if (response == -1)
                image.at<Vec3b>(i,j)  = blue;
        }

// Show the training data
        int thickness = -1;
        int lineType = 8;
        circle( image, Point(501,  10), 5, Scalar(  0,   0,   0), thickness, lineType);
        circle( image, Point(255,  10), 5, Scalar(255, 255, 255), thickness, lineType);
        circle( image, Point(501, 255), 5, Scalar(255, 255, 255), thickness, lineType);
        circle( image, Point( 10, 501), 5, Scalar(255, 255, 255), thickness, lineType);

// Show support vectors
        thickness = 2;
        lineType  = 8;
        int c     = SVM.get_support_vector_count();

        for (int i = 0; i < c; ++i)
        {
            const float* v = SVM.get_support_vector(i);
            circle( image,  Point( (int) v[0], (int) v[1]),   6,   Scalar(128, 128, 128), thickness, lineType);
        }

        imwrite("result.png", image);        // save the image

        imshow("SVM Simple Example", image); // show it to the user
        waitKey(0);

}

I am not able to implement the train function. 我无法实现火车功能。 It says that the function is not found. 它说找不到该功能。 Please help me out with a newer version of this code. 请帮助我使用此代码的较新版本。

You have several errors in your code. 您的代码中有几个错误。 Some are C++ syntactic errors, some are due the fact that you are using OpenCV 2.4.X api, which is different from OpenCV 3.0 有些是C ++语法错误,有些是由于您使用的是OpenCV 2.4.X api而与OpenCV 3.0不同

1) When you are referring to the svm instance, you should use svm (the variable name), not SVM the class name. 1)在引用svm实例时,应使用svm (变量名),而不是SVM的类名。

2) In the case of classification problem the responses must be categorical. 2)在分类问题的情况下,回答必须是分类的。 So 所以

float labels[4] = { 1.0, -1.0, -1.0, -1.0 };
Mat labelsMat(4, 1, CV_32FC1, labels);

should be: 应该:

int labels[4] = { 1, -1, -1, -1 };
Mat labelsMat(4, 1, CV_32SC1, labels); 

3) train accepts different parameters. 3) train接受不同的参数。 SVM->train(trainingDataMat, labelsMat, Mat(), Mat(), svm); should be: svm->train(trainingDataMat, ROW_SAMPLE, labelsMat); 应为: svm->train(trainingDataMat, ROW_SAMPLE, labelsMat);

4) get_support_vector_count doesn't exists in OpenCV 3.0. 4) get_support_vector_count在OpenCV 3.0中不存在。 int c = SVM.get_support_vector_count(); should be: int c = svm->getSupportVectors().rows; 应该是: int c = svm->getSupportVectors().rows;

5) get_support_vector doesn't exists in OpenCV 3.0. 5) get_support_vector在OpenCV 3.0中不存在。 const float* v = SVM.get_support_vector(i); should be: const float* v = svm->getSupportVectors().ptr<float>(i); 应该是: const float* v = svm->getSupportVectors().ptr<float>(i);


The code in this answer already works as expected. 答案中的代码已按预期工作。 If you introduce such errors it won't work, obviously. 如果您引入此类错误,则显然将无法正常工作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM