安装及部分使用,此教程很详细:https://blog.csdn.net/qq_31781741/article/details/82666861
本文是对教程的补充,如:参数优化,通过代码训练、测试等
安装
跟着上面的教程做就vans(新手一般没有安装TDM-GCC编译器,点教程里的‘谦恭’链接)
使用
一、手动数据标准化(根据上面教程来的,较复杂,不建议)
1)标准格式转换(细节补充)
![](https://img-blog.csdnimg.cn/20200512202747278.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dlaXhpbl80MjkyMDc4MA==,size_16,color_FFFFFF,t_70)
![](https://img-blog.csdnimg.cn/2020051220302769.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dlaXhpbl80MjkyMDc4MA==,size_16,color_FFFFFF,t_70)
2)数据归一化(细节补充)
教程将工具箱放在D盘,如果放在C盘,想改C盘路径方法:cd '路径’
再通过代码进行参数寻优、训练、预测
二、代码数据标准化(含全过程)
% I. 清空环境变量
clear all
clc
%% II. 导入数据
% matrix = xlsread('SVM_feature.xlsx', '安慰', 'A2:E18075'); % 创建特征矩阵
% label = xlsread('SVM_feature.xlsx', '标签', 'C2:C18075'); % 创建label
load SVM_feature_wei.mat % 将保存的matrix、label导入
%%
% 1. 随机产生训练集和测试集
n = randperm(size(matrix,1)); % 代码后面再次利用n,注意会被覆盖
%%
% 2. 训练集——70%样本--安慰12652
train_num = round(0.7*length(label)); % round 四舍五入取整
train_matrix = matrix(n(1:train_num),:);
train_label = label(n(1:train_num),:);
%%
% 3. 测试集——30%样本--安慰5422
test_matrix = matrix(n(train_num + 1:end),:);
test_label = label(n(train_num + 1:end),:);
III. 数据归一化
[Train_matrix,PS] = mapminmax(train_matrix'); %归一化到[-1,1]
Train_matrix = Train_matrix';
Test_matrix = mapminmax('apply',test_matrix',PS);
Test_matrix = Test_matrix';
目的:使预处理的数据被限定在一定的范围内(比如[0,1]或者[-1,1]),从而消除奇异样本数据导致的不良影响。
具体拓展可见:https://blog.csdn.net/u011089523/article/details/80198312
![](https://img-blog.csdnimg.cn/20200514172004242.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dlaXhpbl80MjkyMDc4MA==,size_16,color_FFFFFF,t_70)
%% IV. SVM创建/训练(RBF核函数)
%%% 1. 寻找最佳c/g参数——交叉验证方法
[c,g] = meshgrid(-10:4:10,-10:4:10); % c、g的范围为[-10,10],步长为4
[m,n] = size(c);
cg = zeros(m,n); % 用来记录每个c,g所达到的acc
eps = 10^(-3); % 设置允许的终止判据(默认0.001)
v = 3; % cross validation的折数,即给测试集分为几部分进行cross validation
bestc = 1; % 输出,最佳的参数c
bestg = 0.1; % 输出,最佳的参数g
bestacc = 0; % 输出,最佳的acc
for i = 1:m
for j = 1:n
cmd = ['-v ',num2str(v),' -t 2',' -c ',num2str(2^c(i,j)),' -g ',num2str(2^g(i,j))]; % '-v 'v折交互检验模式 ' -t 2'RBF核函数类型
cg(i,j) = svmtrain(train_label,Train_matrix,cmd); % svmtrain用到-v,得到的不是结构体,对于分类问题,得到的是交叉检验下的平均分类准确率
if cg(i,j) > bestacc
bestacc = cg(i,j);
bestc = 2^c(i,j);
bestg = 2^g(i,j);
end
if abs( cg(i,j)-bestacc )<=eps && bestc > 2^c(i,j)
bestacc = cg(i,j);
bestc = 2^c(i,j);
bestg = 2^g(i,j);
end
end
end
cmd = [' -t 2',' -c ',num2str(bestc),' -g ',num2str(bestg)]; % '-t 2'RBF核函数 -c 16 -g 5.6569
%%
% 2. 创建/训练SVM模型
model = svmtrain(train_label,Train_matrix,cmd);
- 使用svmtrain函数出错“svmtrain has been removed. Use fitcsvm instead”的解决方法:https://blog.csdn.net/inter_xuxing/article/details/7612429
- 这里利用网格搜索法对c、g进行参数寻优时,准确率在一定范围内不变。当c、g范围够大时,准确率才发生变化(不知道是否正常)
- 还有值得注意的是,参数寻优时,训练集的不同分组也会影响准确率,可以多分几次,选择最好的
- libsvm函数参数含义、核函数及参数选择具体见后文“拓展”
%% V. SVM仿真测试
[predict_label_1,accuracy_1,prob_estimates] = svmpredict(train_label,Train_matrix,model);
[predict_label_2] = svmpredict(test_label,Test_matrix,model);
result_1 = [train_label predict_label_1];
result_2 = [test_label predict_label_2];
评价及画图
act = test_label; %真实标签:
act = act';
det = predict_label_2; %预测的标签
det=det';
confusion_matrix1(act,det) %调用confusion_matrix1()函数,具体见下面的链接
ROC:
拓展
- libsvm学习笔记-参数设置
- Libsvm svmtrain和svmpredict以及参数简介
- SVM的算法原理(推荐程度依次递减)
https://zhuanlan.zhihu.com/p/31886934
https://www.jianshu.com/p/bcf069ff9dd3
http://www.blogjava.net/zhenandaci/archive/2009/02/13/254519.html
- LIBSVM中提供的核函数及参数选择
c是惩罚系数,即对误差的宽容度。c越高,说明越不能容忍出现误差,容易过拟合。c越小,容易欠拟合。
1、线性核函数
,没有专门需要设置的参数
2、多项式核函数
,有三个参数。
-d用来设置多项式核函数的最高此项次数,也就是公式中的d,默认值是3。
-g用来设置核函数中的gamma参数设置,也就是公式中的第一个r(gamma),默认值是1/k(k是类别数)。
-r用来设置核函数中的coef0,也就是公式中的第二个r,默认值是0。
3、RBF核函数(高斯核函数)
,有一个参数。
-g用来设置核函数中的gamma参数设置,也就是公式中的第一个r(gamma),默认值是1/k(k是类别数)。
参数c、g的具体含义见:https://blog.csdn.net/wusecaiyun/article/details/49681431
4、sigmoid核函数
,有两个参数。
-g用来设置核函数中的gamma参数设置,也就是公式中的第一个r(gamma),默认值是1/k(k是类别数)。
-r用来设置核函数中的coef0,也就是公式中的第二个r,默认值是0。
常用的SVM参数选择方法有:交叉验证法与网格搜索法