2016-07-13 3 views
0
#include <opencv2/core.hpp> 
#include <opencv2/imgproc.hpp> 
#include "opencv2/imgcodecs.hpp" 
#include <opencv2/highgui.hpp> 
#include <opencv2/ml.hpp> 
using namespace cv; 
using namespace cv::ml; 
using namespace std; 

int main() 
{ 
Mat img_mat = imread("/home/buddhika/workspace/project/images/t.jpg"); 

// Load images in the C++ format 
Size size(64,124);//the image size,e.g.64x124 
resize(img_mat ,img_mat ,size);//resize image 

int num_files = 1;//number of images 
int img_area = 64*124;//imag size 
//initialize the training matrix 
//The number of rows in the matrix would be 5, and the number of columns would be the area of the image, 64*124 = 12 
Mat training_mat(num_files,img_area,CV_32FC1); 
// "fill in" the rows of training_mat with the data from each image. 
cvtColor(img_mat,img_mat, CV_RGB2GRAY); 
imshow("",img_mat); 

int ii = 0; // Current column in training_mat 
//Do this for every training image 
int file_num=0; 
for (int i = 0; i<img_mat.rows; i++) { 
    for (int j = 0; j < img_mat.cols; j++) { 
     training_mat.at<float>(file_num,ii++) = img_mat.at<uchar>(i,j); 
    } 
} 

// training matrix set up properly to pass into the SVM functions 
//set up labels for each training image 
//1D matrix, where each element in the 1D matrix corresponds to each row in the 2D matrix. 
//-1 for non-human and 1 for human 
//labels matrix 
float label = 1.0; 
cout << training_mat.rows<< endl; 
cout << training_mat.cols<< endl; 
Mat labels(1,7936 , CV_32SC1, label); 

// Set up SVM's parameters 
    Ptr<SVM> svmOld = SVM::create(); 
    svmOld->setType(SVM::C_SVC); 
    svmOld->setKernel(SVM::LINEAR); 
    // svmOld->setTermCriteria(TermCriteria(TermCriteria::MAX_ITER, 100, 1e-6)); 

    //train it based on your data 

    svmOld->train(training_mat, ROW_SAMPLE, labels); 
    //same svm 
    svmOld->save("positive.xml"); 


    //Initialize SVM object 
    Ptr<SVM> svmNew = SVM::create(); 
    //Load Previously saved SVM from XML 
    //can save the trained SVM so you don't have to retrain it every time 
    svmNew = SVM::load<SVM>("positive.xml"); 

//To test your images using the trained SVM, simply read an image, convert it to a 1D matrix, and pass that in to svm 
// td.predict(training_mat);//It will return a value based on what you set as your labels 

waitKey(0); 
return(0); 
} 

SVM을 사용한 양성 데이터 트레인에 사용한 코드입니다. 그러나SVM 및 opencv를 사용하는 이미지 트레인

svmOld->train(training_mat, ROW_SAMPLE, labels); 

코드가 추락하여 다음과 같은 오류가 발생합니다. 나는 이것을 어떻게 극복 했는가?

OpenCV Error: Bad argument (in the case of classification problem the responses must be categorical; either specify varType when creating TrainData, or pass integer responses) in train, file /home/buddhika/Documents/OpenCV/modules/ml/src/svm.cpp, line 1618 terminate called after throwing an instance of 'cv::Exception'

답변

0

당신이 열을을 작성하는 동안 샘플이 training_mat의 행에 있는지 지정하는 때문입니다.

다음과 같이 훈련 행렬이어야 만드는 코드 :

Mat training_mat(img_area,num_files,CV_32FC1); 
// "fill in" the rows of training_mat with the data from each image. 
cvtColor(img_mat,img_mat, CV_RGB2GRAY); 
imshow("",img_mat); 

int ii = 0; // Current column in training_mat 
//Do this for every training image 
int file_num=0; 
for (int i = 0; i<img_mat.rows; i++) { 
    for (int j = 0; j < img_mat.cols; j++) { 
     training_mat.at<float>(ii++,file_num) = img_mat.at<uchar>(i,j); 
    } 
} 

을 그리고 당신의 labels도 변경해야합니다 : Mat labels(training_mat.rows,1 , CV_32SC1, label);

+0

SVM 파일을 생성합니다. 하지만 그것은 비어 있으며 여전히 위의 오류가 있습니다. –

0

내가 오른쪽이나하지 오전 모르겠지만, 나는 그것을 시험해보고 싶다.

지금 당신의 질문에 대해 이야기합니다. 문제는 SVM의 구현 인 것 같습니다. 먼저 SVC의 opencv 구현을 먼저 공부하는 것이 좋습니다. https://docs.opencv.org/2.4/doc/tutorials/ml/introduction_to_svm/introduction_to_svm.html

SVM 문서에서 알 수있는 점은 클래스 레이블이 포함 된 교육용 DataSet을 먼저 제공해야한다는 것입니다. 제공된 교육 데이터를 기반으로 SVM을 교육합니다. 또한 양성 라벨뿐만 아니라 양성 라벨에 대해서도 교육해야합니다.

조용한 잘못입니다. 내 컴퓨터에서 코드를 실행하고 일부 디버깅을 수행했습니다. 이 디버깅 된 코드를 사용하십시오.

Mat img_mat = imread("C:\\Users\\saurabh chandra\\Desktop\\52.png"); 
Mat img_mat1 = imread("C:\\Users\\saurabh chandra\\Desktop\\53.png"); 
Size size(64, 124);     
resize(img_mat, img_mat, size); 
resize(img_mat1, img_mat1, size); 
int num_files = 2;    
int img_area = 64 * 124;  


cvtColor(img_mat, img_mat, CV_RGB2GRAY); 
cvtColor(img_mat1, img_mat1, COLOR_BGR2GRAY); 

int ii = 0; 

int file_num = 0; 
for (int i = 0; i<img_mat.rows; i++) 
{ 
for (int j = 0; j < img_mat.cols; j++) 
{ 
    training_mat.at<float>(file_num, ii++) = img_mat.at<uchar>(i, j); 
} 

} 

ii = 0; 
file_num =file_num+1; 

for (int i = 0; i<img_mat.rows; i++) 
    { 
    for (int j = 0; j < img_mat.cols; j++) 
    { 
     training_mat.at<float>(file_num, ii++) = img_mat.at<uchar>(i, j); 
    } 
    } 


float label[2] = { 1.0,1.0 }; 
cout << training_mat.rows << endl; 
cout << training_mat.cols << endl; 
Mat labels(2, 1, CV_32SC1, label); 

Ptr<SVM> svmOld = SVM::create(); 
svmOld->setType(SVM::C_SVC); 
svmOld->setKernel(SVM::LINEAR); 
svmOld->setTermCriteria(TermCriteria(TermCriteria::MAX_ITER, 100, 1e-6)); 

svmOld->train(training_mat, ROW_SAMPLE, labels); 
svmOld->save("positive.xml"); 

waitKey(0); 
return 0; 
} 

이 코드는 SVM 교육 결과를 Positive.xml 파일로 저장합니다.이 코드는 두 개의 이미지에 대해 구현되었습니다. 하지만 더 나은 결과를 얻기 위해 훌륭한 교육 자료를 사용하는 것이 좋습니다.

SVM 구현에 대한 자세한 내용은 여기를 참조하십시오. 이 알려

using OpenCV and SVM with images

도움합니다.

관련 문제