2023年数学建模:支持向量机在数学建模中的应用

news/2024/11/28 9:44:10/

2023年9月数学建模国赛期间提供ABCDE题思路加Matlab代码,专栏链接(赛前一个月恢复源码199,欢迎大家订阅):http://t.csdn.cn/Um9Zd

目录

引言

支持向量机原理

1. 数学原理

2. 核函数

MATLAB实现

数学建模案例

总结


引言

支持向量机(Support Vector Machine,简称SVM)是一种广泛应用于分类和回归任务的方法。它的核心思想是寻找一个最大间隔超平面以分割数据。本文将详细介绍支持向量机的原理、MATLAB实现以及一个数学建模案例,帮助大家更好地理解和应用支持向量机。

支持向量机原理

1. 数学原理

支持向量机的目标是找到一个最大间隔超平面,使得不同类别的样本尽可能地被分隔开。假设我们的样本数据为$X$(每行为一个样本,每列为一个特征),对应的目标变量为$y$(取值为-1或1)。支持向量机模型可以表示为:

$$
y_i(w^T x_i + b) \ge 1 - \xi_i, \quad \xi_i \ge 0, \quad i = 1, 2, \dots, n
$$

其中,$w$表示超平面的法向量,$b$表示截距,$\xi_i$表示松弛变量(用于处理非线性可分的情况)。

为了找到最大间隔超平面,我们需要最小化以下目标函数:

$$
\min_{w, b, \xi} \frac{1}{2} ||w||^2 + C \sum_{i=1}^n \xi_i
$$

$$
\text{subject to } y_i(w^T x_i + b) \ge 1 - \xi_i, \quad \xi_i \ge 0, \quad i = 1, 2, \dots, n
$$

其中,$C$是一个正则化系数,用于控制模型的复杂度。

为了求解这个优化问题,我们可以引入拉格朗日乘子将其转化为对偶问题。具体来说,我们定义拉格朗日函数$L(w, b, \xi, \alpha, \beta)$:

$$
L(w, b, \xi, \alpha, \beta) = \frac{1}{2} ||w||^2 + C \sum_{i=1}^n \xi_i - \sum_{i=1}^n \alpha_i [y_i(w^T x_i + b) - 1 + \xi_i] - \sum_{i=1}^n \beta_i \xi_i
$$

其中,$\alpha_i$和$\beta_i$分别是第$i$个约束的拉格朗日乘子。通过求解拉格朗日对偶问题,我们可以得到最优的$w$和$b$:

$$
w^* = \sum_{i=1}^n \alpha_i^* y_i x_i
$$

$$
b^* = \frac{1}{N_S} \sum_{i \in S}(y_i - w^{*T} x_i)
$$

其中,$S$表示支持向量的集合,$N_S$表示支持向量的个数。

2. 核函数

对于非线性可分的数据,我们可以通过引入核函数(Kernel Function)将原始特征空间映射到高维空间,从而使得数据在高维空间中变得线性可分。常用的核函数有:

  • 线性核函数(Linear Kernel):$K(x_i, x_j) = x_i^T x_j$
  • 多项式核函数(Polynomial Kernel):$K(x_i, x_j) = (x_i^T x_j + c)^d$
  • 高斯核函数(Gaussian Kernel):$K(x_i, x_j) = e^{-\frac{||x_i - x_j||^2}{2 \sigma^2}}$
  • Sigmoid核函数:$K(x_i, x_j) = \tanh(\gamma x_i^T x_j + c)$

引入核函数后,支持向量机的对偶问题可以表示为:

$$
\max_{\alpha} \sum_{i=1}^n \alpha_i - \frac{1}{2} \sum_{i=1}^n \sum_{j=1}^n \alpha_i \alpha_j y_i y_j K(x_i, x_j)
$$

$$
\text{subject to } \sum_{i=1}^n \alpha_i y_i = 0, \quad 0 \le \alpha_i \le C, \quad i = 1, 2, \dots, n
$$

MATLAB实现

接下来,我们将使用MATLAB实现一个简单的支持向量机分类器。我们将使用quadprog函数来求解优化问题。

function [w, b, support_vectors] = svm_train(X, y, C, kernel_function, kernel_params)% 输入参数:%   X: 训练样本矩阵,每行为一个样本,每列为一个特征%   y: 训练样本的目标变量(取值为-1或1)%   C: 正则化系数%   kernel_function: 核函数%   kernel_params: 核函数的参数%% 输出参数:%   w: 超平面的法向量%   b: 超平面的截距%   support_vectors: 支持向量的索引% 计算核矩阵K = kernel_function(X, X, kernel_params);% 构建二次规划问题H = (y * y') .* K;f = -ones(size(X, 1), 1);A = [];b = [];Aeq = y';beq = 0;lb = zeros(size(X, 1), 1);ub = C * ones(size(X, 1), 1);x0 = [];% 求解二次规划问题options = optimoptions('quadprog', 'Display', 'off');alpha = quadprog(H, f, A, b, Aeq, beq, lb, ub, x0, options);% 计算w和bw = X' * (alpha .* y);support_vectors = find(alpha > 1e-4);b = mean(y(support_vectors) - X(support_vectors, :) * w);endfunction y_pred = svm_predict(X, w, b)% 输入参数:%   X: 测试样本矩阵,每行为一个样本,每列为一个特征%   w: 超平面的法向量%   b: 超平面的截距%% 输出参数:%   y_pred: 预测结果(取值为-1或1)y_pred = sign(X * w + b);endfunction K = linear_kernel(X1, X2, ~)% 线性核函数K = X1 * X2';
endfunction K = polynomial_kernel(X1, X2, params)% 多项式核函数c = params(1);d = params(2);K = (X1 * X2' + c) .^ d;
endfunction K = gaussian_kernel(X1, X2, params)% 高斯核函数sigma = params(1);K = exp(-pdist2(X1, X2, 'squaredeuclidean') / (2 * sigma^2));
endfunction K = sigmoid_kernel(X1, X2, params)% Sigmoid核函数gamma = params(1);c = params(2);K = tanh(gamma * X1 * X2' + c);
end

数学建模案例

为了说明支持向量机在数学建模中的应用,我们将使用一个虚拟的二分类问题作为示例。假设我们有一组二维数据点,每个数据点对应一个类别(-1或1)。我们的任务是找到一个能够尽可能准确地分隔这两类数据点的超平面。

首先,我们生成一些模拟数据并可视化:

% 生成模拟数据
rng(0);
n_samples =100;
X = [randn(n_samples, 2); randn(n_samples, 2) + 2];
y = [ones(n_samples, 1); -ones(n_samples, 1)];% 可视化模拟数据
figure;
scatter(X(y == 1, 1), X(y == 1, 2), 'r', 'filled', 'MarkerEdgeColor', 'k');
hold on;
scatter(X(y == -1, 1), X(y == -1, 2), 'b', 'filled', 'MarkerEdgeColor', 'k');
xlabel('Feature 1');
ylabel('Feature 2');
legend('Class 1', 'Class -1');
title('Simulated Data');
grid on;% 训练支持向量机
C = 1;
kernel_function = @linear_kernel;
kernel_params = [];
[w, b, support_vectors] = svm_train(X, y, C, kernel_function, kernel_params);% 可视化支持向量机的决策边界
x1_range = linspace(min(X(:, 1)) - 1, max(X(:, 1)) + 1, 100);
x2_range = linspace(min(X(:, 2)) - 1, max(X(:, 2)) + 1, 100);
[X1, X2] = meshgrid(x1_range, x2_range);
X_grid = [X1(:), X2(:)];
y_grid = svm_predict(X_grid, w, b);
Y = reshape(y_grid, size(X1));figure;
scatter(X(y == 1, 1), X(y == 1, 2), 'r', 'filled', 'MarkerEdgeColor', 'k');
hold on;
scatter(X(y == -1, 1), X(y == -1, 2), 'b', 'filled', 'MarkerEdgeColor', 'k');
contour(X1, X2, Y, [0, 0], 'k', 'LineWidth', 1);
scatter(X(support_vectors, 1), X(support_vectors, 2), 100, 'k', 'o', 'LineWidth', 1);
xlabel('Feature 1');
ylabel('Feature 2');
legend('Class 1', 'Class -1', 'Decision Boundary', 'Support Vectors');
title('SVM Decision Boundary');
grid on;

上述代码将生成两幅图像。第一幅图像展示了模拟的二维数据,其中红色和蓝色点分别表示类别1和类别-1。第二幅图像展示了支持向量机的决策边界,黑色实线表示超平面,黑色圆圈表示支持向量。从图中可以看出,支持向量机成功地找到了一个能够很好地分隔两类数据的超平面。

总结

本文介绍了支持向量机的原理、MATLAB实现以及一个数学建模案例。支持向量机是一种强大的分类和回归方法,具有很好的理论基础和实践效果。希望本文能帮助大家更好地理解和应用支持向量机在实际问题中。


http://www.ppmy.cn/news/109789.html

相关文章

Linux 上安装 PostgreSQL——Ubuntu

打开 PostgreSQL 官网 PostgreSQL: The worlds most advanced open source database,点击菜单栏上的 Download ,可以看到这里包含了很多平台的安装包,包括 Linux、Windows、Mac OS等 。 Linux 我们可以看到支持 Ubuntu 和 Red Hat 等各个平台…

vue项目案例(Vue3)

本篇文章主要是,使用 vite 创建一个vue3 项目,实践 vie-router4 vuex4 结合 componsition API 的使用。目的是让未接触过 vue3 的同学快速上手。 一、vue3.0 创建项目 vue3 创建项目的时候有两种方式,第一种就是官方推荐的 vite 。另外一种就…

【C/C++】之内存管理(超详细练气篇)

个人主页:平行线也会相交💪 欢迎 点赞👍 收藏✨ 留言✉ 加关注💓本文由 平行线也会相交 原创 收录于专栏【C之路】💌 本专栏旨在记录C的学习路线,望对大家有所帮助🙇‍ 希望我们一起努力、成长&…

[RUST/腐蚀]Windows-开服服务端下载以及配置

一、前置要求 1.SteamCMD:SteamCMD - Valve Developer Communityhttps://developer.valvesoftware.com/wiki/SteamCMD 2.通过SteamCMD下载RUST/腐蚀服务端。 二、SteamCMD 注意:所有目录均应避免出现中文。 1.建立SteamCMD文件夹,如 D:\st…

达梦数据库8安装教程

第一步:双击驱动 注意:如果双击显示没有驱动,则安装WinCDEmu软件。 第二步:双击setup.exe安装包 第三步:选择时区 第四步:验证key文件 因为我们是免费试用,所以没有key文件,直接下一…

【笔记】【Javascript】javascript实现继承

前言 之前写过关于面向对象编程的文章,通过阅读别人的博客了解了一下Javascript实现继承的方法,并且使用图画的形式帮助了解,图是自己做的,若有偏差请读者帮忙指出,谢谢。笔记中有些个人理解后整理的笔记,…

MATLAB当中线性方程组、不定方程组、奇异方程组、超定方程组的介绍

系列文章目录 MATLAB绘图函数的相关介绍——海底测量、二维与三维图形绘制 MATLAB求函数极限的简单介绍 文章目录 一、线性方程组 1.1、线性方程组简介 1.2、矩阵的初等变换 1.3、MATLAB举例 二、对于MATLAB几个函数的解释 2.1、reff()函数 2.2、inv()函数 2.3、其他…

C++程序设计基础【二】

C程序设计基础【二】 一、类的概念1.类和实例的来源1.属性2.行为 2.程序中的类和对象1.数据成员2.成员函数 二、类1.类定义1.声明数据成员2.声明成员函数3.访问修饰符4.数据成员的访问修饰符5.成员函数的访问修饰符6.分组访问修饰符 2.成员函数定义3.内联函数1.隐式内联函数2.显…