如何从LibSVM模型手动解析支持向量进行分类?

时间:2013-10-09 18:14:36

标签: machine-learning svm libsvm

据我所知,我可以使用LibSVM从一组数据训练产生的模型中解析支持向量。

生成分类器的公式是什么?

我是否需要文件标题中的数据,如下所示(内核等...在列出的支持向量之前):

 svm_type c_svc
 kernel_type rbf
 gamma 0.125
 nr_class 4
 total_sv 1038
 rho -0.859244 -0.876628 -0.958343 0.543365 -1.10722 -1.79433
 label 2 1 3 0
 nr_sv 364 276 242 156
 SV

我的情况是

  • 我想从Node.JS做分类。但是,LibSVM还没有绑定它。
  • 由于我的模型不会改变,我想在Node.JS中进行分类,将模型保存在内存中。
  • 如果这被证明是慢的,我宁愿在C ++中从头开始编写相同的分类,并创建一个包装器模块,如果它只是一个简单的计算(我怀疑它是)。

感谢。

1 个答案:

答案 0 :(得分:1)

您应该能够将C函数转换为Javascript。

以下是相关代码:

double svm_predict_values(const svm_model *model, const svm_node *x, double* dec_values)
{
        int i;
        int nr_class = model->nr_class;
        int l = model->l;

        double *kvalue = Malloc(double,l);
        for(i=0;i<l;i++)
                kvalue[i] = Kernel::k_function(x,model->SV[i],model->param);

        int *start = Malloc(int,nr_class);
        start[0] = 0;
        for(i=1;i<nr_class;i++)
                start[i] = start[i-1]+model->nSV[i-1];

        int *vote = Malloc(int,nr_class);
        for(i=0;i<nr_class;i++)
                vote[i] = 0;

        int p=0;
        for(i=0;i<nr_class;i++)
                for(int j=i+1;j<nr_class;j++)
                {
                        double sum = 0;
                        int si = start[i];
                        int sj = start[j];
                        int ci = model->nSV[i];
                        int cj = model->nSV[j];

                        int k;
                        double *coef1 = model->sv_coef[j-1];
                        double *coef2 = model->sv_coef[i];
                        for(k=0;k<ci;k++)
                                sum += coef1[si+k] * kvalue[si+k];
                        for(k=0;k<cj;k++)
                                sum += coef2[sj+k] * kvalue[sj+k];
                        sum -= model->rho[p];
                        dec_values[p] = sum;

                        if(dec_values[p] > 0)
                                ++vote[i];
                        else
                                ++vote[j];
                        p++;
                }

        int vote_max_idx = 0;
        for(i=1;i<nr_class;i++)
                if(vote[i] > vote[vote_max_idx])
                        vote_max_idx = i;

        free(kvalue);
        free(start);
        free(vote);
        return model->label[vote_max_idx];
}

请注意,您必须重新创建此等式:

enter image description here

唯一的区别是因为你的模型有4个类,你需要实现投票系统,这基本上就是上面的代码。

希望它有所帮助。