【问题标题】:How to do classification manually parsing the support vectors from LibSVM model?如何从 LibSVM 模型中手动解析支持向量进行分类?
【发布时间】:2013-10-17 06:12:38
【问题描述】:

据我所知,我可以从使用 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++ 中从头开始编写相同的分类并创建一个包装器模块,如果它只是一个简单的计算问题(我怀疑是这样)。

谢谢。

【问题讨论】:

  • 如果你仍然对在节点上使用 libsvm 感兴趣,有一个名为node-svm的库
  • 谢谢,我已经从 libsvm 的源代码中用 JavaScript 重写了分类,但还没有发布。这对于可以接受二进制依赖的人来说应该更好。

标签: machine-learning svm libsvm


【解决方案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];
}

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

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

希望对你有帮助。

【讨论】:

  • 谢谢@Pedrom。您的答案是否缺少您提到的方程式?至于上面的代码——你已经从 LibSVM 的源代码中删除了这个函数:github.com/arnaudsj/libsvm/blob/master/svm.cpp#L2459 Nice。 :)
  • 糟糕...由于某种原因它没有显示...现在已修复 :)模型不是二进制的,因为它可能更容易。
猜你喜欢
  • 2013-02-26
  • 2016-06-05
  • 2014-01-05
  • 2013-04-04
  • 2014-06-28
  • 2010-12-29
  • 2017-11-30
  • 2013-05-25
  • 2018-05-28
相关资源
最近更新 更多