1
votes

I have some doubts about how to correctly use the libSVM C++ code. Using my own matricies of data I've trained a binary SVM classifier using the svm-train exe provided by the author. I've also tested the model using the svm-predict executable. The train and test matrices have been created as suggested by the authors:

label 1:val_1.....n:val_n

label 1:val_1.....n:val_n

label 1:val_1.....n:val_n

.....

label 1:val_1.....n:val_n

The model seems to work fine in this way.

At the moment what I'm trying to do is to load the model from a C++ application and ask for classification. I think the problem is when I create the svm_node array, what I do is the following

Mat featureVector = ....; //opencv matrix 1 rows x n cols
int n = featureVector.cols;
struct svm_node *x = (struct svm_node *) malloc((n+1)*sizeof(struct svm_node));

int nonZero = 0;
for(int i = 0; i < n; i++){
    //Escape zero values
    if(featureVector.at<float>(0,i) != 0){
        x[nonZero].index = i+1; //libsvm index start from 1
        x[nonZero].value = featureVector.at<float>(0,i);
        nonZero++;
    }
}
x[nonZero].index = -1;//requested by libSVM

x = (struct svm_node *) realloc(x, (nonZero+1) * sizeof(struct svm_node));

//finally ask for prediction
int prediction = svm_predict(model, x);

The classifier just produce always the same result. I'm not sure if I have to escape the zero values anyway if I don't the result is the same. Does anyone know if I'm doing something wrong?

2

2 Answers

0
votes

I managed to solve the problem, what is wrong in my code is the start index of the first feature. So conversely to what I read in other post, the libsvm index starts from zero. Using the following code, the classifier works correctly:

int n = featureVector.cols;
struct svm_node *x = (struct svm_node *) malloc((n+1)*sizeof(struct svm_node));

for(int i = 0; i < n; i++){

        x[i].index = i; 
        x[i].value = featureVector.at<float>(0,i);

}

x[n].index = -1;

I've also removed the skip-zero control. Hope this could help someone!

Source svm-predict.c code from the author.

0
votes

You need to have same number of samples in training set. As an Example; classA has 500 instances. classB has 500 instances. Otherwise, you will get all result same with the larger class that you have used in training set.