【问题标题】:Unsupported format or combination of formats (Input sample must have 32fC1 type) in cvPreparePredictDatacvPreparePredictData 中不支持的格式或格式组合(输入样本必须具有 32fC1 类型)
【发布时间】:2016-05-26 16:45:43
【问题描述】:

我尝试训练自己的 SVM 来检测人,我将图像序列的大小全部调整为 320x240。我在训练过程中将图像转换为灰色,而我在测试时将测试图像转换为灰色,但出现错误。

#include <opencv2/opencv.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv/cv.h>
#include <iostream>
#include <vector>

#include <stdio.h>
#include <opencv2/features2d/features2d.hpp>
#include <opencv2/nonfree/features2d.hpp>
#include <fstream>

using namespace std;
using namespace cv;

int main(int argc, char* argv[]) {
    String folder = "output/*.jpg";
    vector<String> filenames;
    glob(folder, filenames);

    Mat gray,gray1;

    int img_area=320*240;
    Mat training_mat(filenames.size(),img_area,CV_32FC1);
    Mat labels(filenames.size(),1,CV_32FC1);

    for(int i = 0; i < 900; i++){
        labels.at<float>(i,0)=1;
    }
    for(int i = 900; i < filenames.size(); i++){
        labels.at<float>(i,0)=-1;
    }

    for (size_t i = 0; i < filenames.size(); ++i){
        Mat img = imread(filenames[i]);
        cvtColor(img, gray, CV_RGB2GRAY);
        int ii = 0; 
        for (int k = 0; k < gray.rows; k++) {
            for (int j = 0; j < gray.cols; j++) {
                training_mat.at<float>(i,ii++) = gray.at<uchar>(k,j);
            }
        }
    }

    CvSVMParams params;
    params.svm_type = CvSVM::C_SVC;
    params.kernel_type = CvSVM::POLY;
    params.gamma = 3;
    params.degree = 3;
    CvSVM svm;
    svm.train(training_mat, labels, Mat(), Mat(), params);
    svm.save("svm_filename"); // saving
    svm.load("svm_filename"); // loading
    Mat image = imread("output/500.jpg");
    cvtColor(image, gray1, CV_RGB2GRAY);
    int response = svm.predict(gray1);

    if(response == 1){
        cout << "person " << endl ;
    }
    return 0;
}

我编译程序时遇到这个错误:

OpenCV 错误:cvPreparePredictData,文件 /home/mourad/opencv/opencv-2.4.10/modules/ml/src/inner_functions.cpp,第 1102 行中不支持的格式或格式组合(输入样本必须具有 32fC1 类型)终止在抛出 'cv::Exception' 的实例后调用

【问题讨论】:

    标签: c++ opencv


    【解决方案1】:

    您也应该将gray1 转换为32FC1

    cvtColor(image, gray1, CV_RGB2GRAY);
    gray1.convertTo(gray1, CV_32FC1, 1.0/255.0); // <-- add this line before predict
    int response = svm.predict(gray1);
    

    另外,请注意,下面的代码不是从 uchar 转换为 float 的正确方法,因为它们应该适用于不同的范围:[0,255][0,1]

    training_mat.at<float>(i,ii++) = gray.at<uchar>(k,j);
    

    【讨论】:

    • :我添加了它我得到了这个错误:cvPreparePredictData中输入数组的大小不正确(输入样本必须是一维向量)
    • 如何将 2D 图像转换为 1D 图像?
    • @para 你应该使用reshapecv::Mat gray_reshaped = gray1.reshape(1,1); 应该这样做。如果这对您有帮助,请点赞或标记为答案。
    【解决方案2】:

    我将此添加到我的程序中:

    cvtColor(image,gray1, CV_RGB2GRAY);
    Mat image_mat(1,img_area,CV_32FC1);
    int jj=0;
    for (int k = 0; k < gray1.rows; k++) {
            for (int j = 0; j < gray1.cols; j++) {
    
            image_mat.at<float>(0,jj++) = gray.at<uchar>(k,j);
            }
        }
    
    int response=svm.predict(image_mat);
    if(response == 1){
    
        cout << "person detected" << endl;
    }
    

    但程序运行并没有显示任何内容。

    【讨论】:

    • 请,发布答案不是更新问题的正确方法。删除它并将新问题添加到您的问题中,而不删除任何以前的信息。另外,如果是全新的问题,正确的做法是再问一个问题。
    猜你喜欢
    • 1970-01-01
    • 2019-02-26
    • 1970-01-01
    • 1970-01-01
    • 2021-12-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多