将 libsvm 模型结构从 matlab 保存到可以在 C++ 中读取的 .model 文件
Saving libsvm model structure from matlab to .model file which can be read in C++
我有两个问题:
- 我按照 post Lib svm, how to convert MyModel.mat to MyModel.model 中的说明进行操作
我尝试使用以下方法在 Mac OSx El Capitan 上构建 svm_savemodel.c:
mex svm_savemodel.c 并且发生了以下情况:
使用 'Xcode with Clang' 构建。为体系结构使用 mex 未定义符号时出错 x86_64:“_matlab_matrix_to_model”,引用自:svm_savemodel.o 中的 _mexFunction “_svm_free_and_destroy_model”,引用自:svm_savemodel.o 中的 _mexFunction “ _svm_save_model”,引用自:svm_savemodel.o ld 中的 _mexFunction:找不到体系结构的符号 x86_64 clang:错误:链接器命令失败,退出代码为 1(使用 -v 查看调用)
谁能提出一些解决方案?
- 所以我在考虑编写一个 matlab 代码,它将 matlab 中的模型结构转换为 MyModel.model 可以在 C++ 中读取的文件
这个postLibsvm model file format No model number讲的是需要保存在.model文件中的参数。
我正在处理回归问题,所以在我的例子中,标签条目将不存在。除此之外还有什么需要注意的吗?
谢谢。
我修改了 How to create training data for libsvm (as an svm_node struct) 处的代码以进行回归,并看到了模型的保存格式
{
结构 svm_parameter 参数; // 由 parse_command_line 设置
结构 svm_problem 概率; // 由 read_problem 设置
//结构svm_model *模型;
结构 svm_node *x_space;
int main(int argc, const char * argv[]) {
char input_file_name[1024];
char model_file_name[1024] = "MyModel" ;
const char *error_msg;
param.svm_type = EPSILON_SVR;
param.eps = 1e-3;
param.C = 1;
//param.kernel_type = RBF;
param.degree = 3;
//Problem definition-------------------------------------------------------------
prob.l = 8;
//x values matrix of xor values
double matrix[prob.l][2];
matrix[0][0] = 0.1;
matrix[0][1] = 0.2;
matrix[1][0] = 0.2;
matrix[1][1] = 0.3;
matrix[2][0] = 0.4;
matrix[2][1] = 0.5;
matrix[3][0] = 0.8;
matrix[3][1] = 0.9;
matrix[4][0] = 0.6;
matrix[4][1] = 0.7;
matrix[5][0] = 0.55;
matrix[5][1] = 0.65;
matrix[6][0] = 0.45;
matrix[6][1] = 0.55;
matrix[7][0] = 0.65;
matrix[7][1] = 0.75;
svm_node** x = Malloc(svm_node*,prob.l);
//Trying to assign from matrix to svm_node training examples
for (int row = 0;row <prob.l; row++){
svm_node* x_space = Malloc(svm_node,3);
for (int col = 0;col < 2;col++){
x_space[col].index = col;
x_space[col].value = matrix[row][col];
}
x_space[2].index = -1; //Each row of properties should be terminated with a -1 according to the readme
x[row] = x_space;
}
prob.x = x;
//yvalues
prob.y = Malloc(double,prob.l);
prob.y[0] = 0.15;
prob.y[1] = 0.25;
prob.y[2] = 0.45;
prob.y[3] = 0.85;
prob.y[4] = 0.65;
prob.y[5] = 0.6;
prob.y[6] = 0.5;
prob.y[7] = 0.7;
//Train model---------------------------------------------------------------------
svm_model *model = svm_train(&prob,¶m);
//svm_model *model = svm_load_model(model_file_name);
//Test model----------------------------------------------------------------------
svm_node* testnode = Malloc(svm_node,3);
testnode[0].index = 0;
testnode[0].value = 0.6;
testnode[1].index = 1;
testnode[1].value = 0.7;
testnode[2].index = -1;
//This works correctly:
double retval = svm_predict(model,testnode);
svm_save_model(model_file_name, model);
printf("retval: %f\n",retval);
svm_destroy_param(¶m);
free(prob.y);
free(prob.x);
free(x_space);
return 0;
}
}
然后我在matlab中写了下面的代码来保存在matlab中生成的svm模型结构,我可以在C++中读取保存的模型
{
负载('ClassificationMATLAB.mat'); % 打开带有svm struct of model的mat文件,struct的变量名是'svm'
fid=fopen('Mymodel','w');
fprintf(fid,'%s %s\n','svm_type','epsilon_svr');
fprintf(fid,'%s %s\n','kernel_type','rbf'); % rbf
fprintf(fid,'%s %s\n','nr_class','2');
% fprintf(fid,'%s %s\n','degree', '3');
fprintf(fid,'%s %s\n','total_sv',num2str(svm.totalSV));
fprintf(fid,'%s %s\n','rho',num2str(svm.rho));
fprintf(fid,'%s\n','SV');
FullSVs=满(svm.SVs);
for i=1:length(svm.SVs)
fprintf(fid, '%s', num2str(svm.sv_coef(i)));
fprintf(fid, '%s %s\n', [' 0:' num2str(FullSVs(i,1))],[' 1:' num2str(FullSVs(i,2))]);
结束
fclose(fid);
}
我有两个问题:
- 我按照 post Lib svm, how to convert MyModel.mat to MyModel.model 中的说明进行操作 我尝试使用以下方法在 Mac OSx El Capitan 上构建 svm_savemodel.c: mex svm_savemodel.c 并且发生了以下情况:
使用 'Xcode with Clang' 构建。为体系结构使用 mex 未定义符号时出错 x86_64:“_matlab_matrix_to_model”,引用自:svm_savemodel.o 中的 _mexFunction “_svm_free_and_destroy_model”,引用自:svm_savemodel.o 中的 _mexFunction “ _svm_save_model”,引用自:svm_savemodel.o ld 中的 _mexFunction:找不到体系结构的符号 x86_64 clang:错误:链接器命令失败,退出代码为 1(使用 -v 查看调用) 谁能提出一些解决方案?
- 所以我在考虑编写一个 matlab 代码,它将 matlab 中的模型结构转换为 MyModel.model 可以在 C++ 中读取的文件 这个postLibsvm model file format No model number讲的是需要保存在.model文件中的参数。
我正在处理回归问题,所以在我的例子中,标签条目将不存在。除此之外还有什么需要注意的吗?
谢谢。
我修改了 How to create training data for libsvm (as an svm_node struct) 处的代码以进行回归,并看到了模型的保存格式
{ 结构 svm_parameter 参数; // 由 parse_command_line 设置 结构 svm_problem 概率; // 由 read_problem 设置 //结构svm_model *模型; 结构 svm_node *x_space;
int main(int argc, const char * argv[]) {
char input_file_name[1024];
char model_file_name[1024] = "MyModel" ;
const char *error_msg;
param.svm_type = EPSILON_SVR;
param.eps = 1e-3;
param.C = 1;
//param.kernel_type = RBF;
param.degree = 3;
//Problem definition-------------------------------------------------------------
prob.l = 8;
//x values matrix of xor values
double matrix[prob.l][2];
matrix[0][0] = 0.1;
matrix[0][1] = 0.2;
matrix[1][0] = 0.2;
matrix[1][1] = 0.3;
matrix[2][0] = 0.4;
matrix[2][1] = 0.5;
matrix[3][0] = 0.8;
matrix[3][1] = 0.9;
matrix[4][0] = 0.6;
matrix[4][1] = 0.7;
matrix[5][0] = 0.55;
matrix[5][1] = 0.65;
matrix[6][0] = 0.45;
matrix[6][1] = 0.55;
matrix[7][0] = 0.65;
matrix[7][1] = 0.75;
svm_node** x = Malloc(svm_node*,prob.l);
//Trying to assign from matrix to svm_node training examples
for (int row = 0;row <prob.l; row++){
svm_node* x_space = Malloc(svm_node,3);
for (int col = 0;col < 2;col++){
x_space[col].index = col;
x_space[col].value = matrix[row][col];
}
x_space[2].index = -1; //Each row of properties should be terminated with a -1 according to the readme
x[row] = x_space;
}
prob.x = x;
//yvalues
prob.y = Malloc(double,prob.l);
prob.y[0] = 0.15;
prob.y[1] = 0.25;
prob.y[2] = 0.45;
prob.y[3] = 0.85;
prob.y[4] = 0.65;
prob.y[5] = 0.6;
prob.y[6] = 0.5;
prob.y[7] = 0.7;
//Train model---------------------------------------------------------------------
svm_model *model = svm_train(&prob,¶m);
//svm_model *model = svm_load_model(model_file_name);
//Test model----------------------------------------------------------------------
svm_node* testnode = Malloc(svm_node,3);
testnode[0].index = 0;
testnode[0].value = 0.6;
testnode[1].index = 1;
testnode[1].value = 0.7;
testnode[2].index = -1;
//This works correctly:
double retval = svm_predict(model,testnode);
svm_save_model(model_file_name, model);
printf("retval: %f\n",retval);
svm_destroy_param(¶m);
free(prob.y);
free(prob.x);
free(x_space);
return 0;
} }
然后我在matlab中写了下面的代码来保存在matlab中生成的svm模型结构,我可以在C++中读取保存的模型
{ 负载('ClassificationMATLAB.mat'); % 打开带有svm struct of model的mat文件,struct的变量名是'svm' fid=fopen('Mymodel','w');
fprintf(fid,'%s %s\n','svm_type','epsilon_svr'); fprintf(fid,'%s %s\n','kernel_type','rbf'); % rbf fprintf(fid,'%s %s\n','nr_class','2'); % fprintf(fid,'%s %s\n','degree', '3');
fprintf(fid,'%s %s\n','total_sv',num2str(svm.totalSV)); fprintf(fid,'%s %s\n','rho',num2str(svm.rho));
fprintf(fid,'%s\n','SV');
FullSVs=满(svm.SVs);
for i=1:length(svm.SVs)
fprintf(fid, '%s', num2str(svm.sv_coef(i)));
fprintf(fid, '%s %s\n', [' 0:' num2str(FullSVs(i,1))],[' 1:' num2str(FullSVs(i,2))]);
结束 fclose(fid);
}