我正在使用BOW模型和SVM开发图像分类项目。 我想找出SVM预测概率,但opencv svm中没有这样的功能。有没有办法做到这一点?我想找出n级SVM中的预测概率。
答案 0 :(得分:3)
不,你不能用CvSVM做到这一点。 OpenCV的SVM实现基于一个非常旧版本的libsvm。下载最新版本的libsvm并改为使用它。当然,您必须编写一个包装器来转换数据格式。见http://www.csie.ntu.edu.tw/~cjlin/libsvm/
答案 1 :(得分:0)
正如我的@Bull所建议的那样,OpenCV中未实现预测概率。但是,有很多种方法可以访问底层libsvm
来实现这一目标。 blog和代码段的详细信息如下:
注意:此函数会加载模型,因此不会在外部加载。
#include "svm.h"
...
void predict(string modelPath, Mat& hist) {
const char *MODEL_FILE = modelPath.c_str();
if ((this->SVMModel = svm_load_model(MODEL_FILE)) == 0) {
this->modelLoaded = false;
fprintf(stderr, "Can't load SVM model %s", MODEL_FILE);
return;
}
struct svm_node *svmVec;
svmVec = (struct svm_node *)malloc((hist.cols+1)*sizeof(struct svm_node));
int j;
for (j = 0; j < hist.cols; j++) {
svmVec[j].index = j+1;
svmVec[j].value = hist.at<float>(0, j);
}
svmVec[j].index = -1; // this is quite essential. No documentation.
double scores[8]; // suppose there are eight classes
if(svm_check_probability_model(SVMModel)) {
svm_predict_probability(SVMModel, svmVec, scores);
}
}
答案 2 :(得分:-1)
您可以尝试生成混淆矩阵,这应该告诉您每个图像属于任何类的概率。 Confusion Matrix
在这里你有一个我发现的片段,虽然它不完整但可能会给你一些想法:
map<string,map<string,int> > confusion_matrix; // confusionMatrix[classA][classB] = number_of_times_A_voted_for_B;
map<string,CvSVM> classes_classifiers; //This we created earlier
vector<string> files; //load up with images
vector<string> classes; //load up with the respective classes
for(..loop over a directory?..) {
Mat img = imread(files[i]),resposne_hist;
vector<KeyPoint> keypoints;
detector->detect(img,keypoints);
bowide->compute(img, keypoints, response_hist);
float minf = FLT_MAX; string minclass;
for (map<string,CvSVM>::iterator it = classes_classifiers.begin(); it != classes_classifiers.end(); ++it) {
float res = (*it).second.predict(response_hist,true);
if (res < minf) {
minf = res;
minclass = (*it).first;
}
}
confusion_matrix[minclass][classes[i]]++;
}
我还没有测试过,所以如果你能让它工作我会很感激你在这里沟通:)