【Math】奇异值分解(SVD)详解及 Python 实现

1. 什么是奇异值分解(SVD)

奇异值分解(Singular Value Decomposition,简称 SVD)是矩阵分解的一种方法,它将任意矩阵 A A A 分解为三个矩阵的乘积:

A = U Σ V T A = U \Sigma V^T A=UΣVT

其中:

  • A A A m × n m \times n m×n 的矩阵。
  • U U U m × m m \times m m×m 的酉矩阵,包含 A A T A A^T AAT 的特征向量。
  • Σ \Sigma Σ 是一个 m × n m \times n m×n 的对角矩阵,包含矩阵 A A A 的奇异值。
  • V T V^T VT n × n n \times n n×n 的酉矩阵,包含 A T A A^T A ATA 的特征向量。

奇异值分解不仅适用于方阵,也适用于任意矩阵。它在信号处理、图像压缩、降维和推荐系统等应用中有着广泛的应用。

2. 计算步骤

步骤 1:计算 A A T A A^T AAT A T A A^T A ATA

首先,我们计算矩阵 A A T A A^T AAT A T A A^T A ATA

  • A A T A A^T AAT 是一个 m × m m \times m m×m 的对称矩阵;
  • A T A A^T A ATA 是一个 n × n n \times n n×n 的对称矩阵。

步骤 2:求解特征值和特征向量

  • A A T A A^T AAT 求特征值和特征向量:矩阵 A A T A A^T AAT 的特征向量构成了矩阵 U U U,它的特征值的平方根是矩阵 A A A 的奇异值。

  • A T A A^T A ATA 求特征值和特征向量:矩阵 A T A A^T A ATA 的特征向量构成了矩阵 V V V,它的特征值的平方根同样是矩阵 A A A 的奇异值。

步骤 3:构建矩阵 U U U Σ \Sigma Σ V T V^T VT

  • U U U 是由 A A T A A^T AAT 的特征向量构成的矩阵。
  • Σ \Sigma Σ 是一个对角矩阵,包含矩阵 A A A 的奇异值(特征值的平方根)。
  • V T V^T VT 是由 A T A A^T A ATA 的特征向量构成的矩阵。

步骤 4:重构矩阵 A A A

最后,我们可以通过公式

A = U Σ V T A = U \Sigma V^T A=UΣVT

重构原矩阵 A A A,并验证是否一致。

3. 例子:求解矩阵 A A A 的奇异值分解

假设我们有一个简单的 3 × 2 3 \times 2 3×2 矩阵 A A A

A = [ 4 0 3 0 0 0 ] A = \begin{bmatrix} 4 & 0 \\ 3 & 0 \\ 0 & 0 \end{bmatrix} A= 430000

我们将按照以下步骤来计算它的奇异值分解(SVD):

步骤 1:计算 A A T A A^T AAT A T A A^T A ATA

首先计算矩阵 A A T A A^T AAT A T A A^T A ATA

A A T = [ 4 0 3 0 0 0 ] [ 4 3 0 0 0 0 ] = [ 16 12 0 12 9 0 0 0 0 ] A A^T = \begin{bmatrix} 4 & 0 \\ 3 & 0 \\ 0 & 0 \end{bmatrix} \begin{bmatrix} 4 & 3 & 0 \\ 0 & 0 & 0 \end{bmatrix} = \begin{bmatrix} 16 & 12 & 0 \\ 12 & 9 & 0 \\ 0 & 0 & 0 \end{bmatrix} AAT= 430000 [403000]= 161201290000

A T A = [ 4 3 0 0 0 0 ] [ 4 0 3 0 0 0 ] = [ 25 0 0 0 ] A^T A = \begin{bmatrix} 4 & 3 & 0 \\ 0 & 0 & 0 \end{bmatrix} \begin{bmatrix} 4 & 0 \\ 3 & 0 \\ 0 & 0 \end{bmatrix} = \begin{bmatrix} 25 & 0 \\ 0 & 0 \end{bmatrix} ATA=[403000] 430000 =[25000]

步骤 2:求解特征值和特征向量

  • A A T A A^T AAT 求特征值和特征向量:

    • 特征值: 25 25 25 0 0 0
    • 对应的特征向量为:
      u 1 = [ 4 5 3 5 0 ] \mathbf{u}_1 = \begin{bmatrix} \frac{4}{5} \\ \frac{3}{5} \\ 0 \end{bmatrix} u1= 54530 u 2 = [ − 3 5 4 5 0 ] \mathbf{u}_2 = \begin{bmatrix} -\frac{3}{5} \\ \frac{4}{5} \\ 0 \end{bmatrix} u2= 53540
  • A T A A^T A ATA 求特征值和特征向量:

    • 特征值: 25 25 25 0 0 0
    • 对应的特征向量为:
      v 1 = [ 1 0 ] \mathbf{v}_1 = \begin{bmatrix} 1 \\ 0 \end{bmatrix} v1=[10] v 2 = [ 0 1 ] \mathbf{v}_2 = \begin{bmatrix} 0 \\ 1 \end{bmatrix} v2=[01]

步骤 3:构建矩阵 U U U Σ \Sigma Σ V T V^T VT

  • 矩阵 U U U A A T A A^T AAT 的特征向量矩阵:
    U = [ 4 5 − 3 5 0 3 5 4 5 0 0 0 1 ] U = \begin{bmatrix} \frac{4}{5} & -\frac{3}{5} & 0 \\ \frac{3}{5} & \frac{4}{5} & 0 \\ 0 & 0 & 1 \end{bmatrix} U= 5453053540001

  • 矩阵 Σ \Sigma Σ 是对角矩阵,包含奇异值:
    Σ = [ 5 0 0 0 0 0 ] \Sigma = \begin{bmatrix} 5 & 0 \\ 0 & 0 \\ 0 & 0 \end{bmatrix} Σ= 500000

  • 矩阵 V T V^T VT A T A A^T A ATA 的特征向量矩阵:
    V T = [ 1 0 0 1 ] V^T = \begin{bmatrix} 1 & 0 \\ 0 & 1 \end{bmatrix} VT=[1001]

步骤 4:重构矩阵 A A A

我们可以通过公式 A = U Σ V T A = U \Sigma V^T A=UΣVT 来重构矩阵 A A A,并验证其正确性。


4. Python 实现

下面是一个 Python 代码实现,使用 numpy 库计算并验证矩阵 A A A 的 SVD。

import numpy as np# 定义矩阵 A
A = np.array([[4, 0],[3, 0],[0, 0]])# 计算 A 的 SVD
U, Sigma, VT = np.linalg.svd(A)# 输出结果
print("U 矩阵:")
print(U)
print("\nSigma (奇异值):")
print(Sigma)
print("\nV^T 矩阵:")
print(VT)# 将 Sigma 转换为对角矩阵形式
Sigma_matrix = np.zeros((A.shape[0], A.shape[1]))
Sigma_matrix[:len(Sigma), :len(Sigma)] = np.diag(Sigma)
print("\nSigma 矩阵:")
print(Sigma_matrix)# 验证 SVD 是否正确,重新构建 A
A_reconstructed = np.dot(U, np.dot(Sigma_matrix, VT))print("\n重构的矩阵 A (U * Sigma * V^T):")
print(A_reconstructed)# 检查重构矩阵与原始矩阵是否接近
print("\n重构矩阵与原矩阵的差异:")
print(A - A_reconstructed)

输出结果

运行代码后,可能得到如下输出:

U 矩阵:
[[ 0.8  0.6  0. ][ 0.6 -0.8  0. ][ 0.   0.   1. ]]Sigma (奇异值):
[5. 0.]V^T 矩阵:
[[1. 0.][0. 1.]]Sigma 矩阵:
[[5. 0.][0. 0.][0. 0.]]重构的矩阵 A (U * Sigma * V^T):
[[4. 0.][3. 0.][0. 0.]]重构矩阵与原矩阵的差异:
[[0. 0.][0. 0.][0. 0.]]

备注

个人水平有限,有问题随时交流~

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/62696.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

桶排序(代码+注释)

#include <stdio.h> #include <stdlib.h>// 定义桶的结构 typedef struct Bucket {int* data; // 动态数组int count; // 当前存储的元素个数int capacity; // 桶的容量 } Bucket;// 初始化桶 void InitBucket(Bucket* bucket) {bucket->capacity 10; // 初…

【Linux】进程控制,手搓简洁版shell

⭐️个人主页&#xff1a;小羊 ⭐️所属专栏&#xff1a;Linux 很荣幸您能阅读我的文章&#xff0c;诚请评论指点&#xff0c;欢迎欢迎 ~ 目录 1、进程创建2、进程终止3、进程等待4、进程程序替换5、手写简洁版shell 1、进程创建 fork函数&#xff1a;从已经存在的进程中创…

雪花算法生成ID

下面将简单介绍雪花算法的简单应用和在web应用中的使用。 雪花算法的组成&#xff1a;雪花算法是由64位组成&#xff1a;符号位(1)、时间戳(41)、机器码(5[数据中心]5[机器ID])、计数器(12) 对于雪花算法的源码可以在这里看&#xff1a;bwmarrin/snowflake: A simple to use …

EasyDarwin搭建直播推流服务

学习链接 easydarwin官网 - 这里看介绍 easydarwin软件下载地址 - 百度网盘 easydarwin视频 B站 文章目录 学习链接使用下载EasyDarwin压缩包&#xff0c;并解压到目录启动EasyDarwin点播直播easyplayer.jsapidocffmpeg推流rtsp & ffplay拉流 使用 下载EasyDarwin压缩包…

云备份实战项目

文章目录 前言一、整体项目简介二、服务端环境及功能简介三、 客户端环境及功能简介四、服务端文件管理类的实现1. 获取文件大小&#xff0c;最后一次修改时间&#xff0c;最后一次访问时间&#xff0c;文件名称&#xff0c;以及文件内容的读写等功能2. 判断文件是否存在&#…

关于ConstarintLayout有关的点

目录 一、概述 二、过程。 1、介绍 主要特点 关键概念 使用示例 总结 2、我遇到的问题 问题&#xff1a; 可能的原因&#xff1a; 结论 一、概述 在学习过程中&#xff0c;发现对ConstarintLayout理解不够到位&#xff0c;下面是发现并解决问题过程。 二、过程。 1…

《数字图像处理基础》学习07-图像几何变换之最近邻插值法放大图像

目录 一&#xff0c;概念 二&#xff0c;题目及matlab实现 1&#xff0c;解题思路 2&#xff0c;matlab实现 1&#xff09;matlab思路 2&#xff09;完整代码 三&#xff0c;放大图像及matlab实现 一&#xff0c;概念 通过上一篇&#xff0c;我已经学习了使用最邻近插…

计网-子网划分

基于本视频观看做的笔记&#xff0c;帮助自己理解 子网掩码&#xff1a;用于识别IP地址中的网络号和主机号的位数 表示方法 第一种.32位二进制数字&#xff0c;在子网掩码中&#xff0c;网络号用”1“表示&#xff0c;主机号用”0“表示 e.g.:IP地址1.1.1.1的子网掩码是255…

【Solidity】入门指南:智能合约开发基础

&#x1f308;个人主页: 鑫宝Code &#x1f525;热门专栏: 闲话杂谈&#xff5c; 炫酷HTML | JavaScript基础 ​&#x1f4ab;个人格言: "如无必要&#xff0c;勿增实体" 文章目录 Solidity入门指南&#xff1a;智能合约开发基础引言1. 开发环境搭建1.1 Remix I…

如何高效地架构一个Java项目

引言 Java是企业级应用开发的主流语言之一&#xff0c;而我们作为使用Java语言的程序员&#xff0c;职称有初级、中级、高级、资深、经理、架构&#xff0c;但我们往往只是慢慢通过经验的积累迭代了自己的等级&#xff0c;如果没有保持学习的习惯&#xff0c;大多数程序员会停留…

HTTP 探秘之旅:从入门到未来

文章目录 导言&#xff1a;目录&#xff1a;第一篇&#xff1a;HTTP&#xff0c;互联网的“快递员”第二篇&#xff1a;从点开网页到看到内容&#xff0c;HTTP 究竟做了什么&#xff1f;第三篇&#xff1a;HTTP 的烦恼与进化史第四篇&#xff1a;HTTP 的铠甲——HTTPS 的故事第…

前端处理sql参数替换问题,即使有重复参数,也可以按顺序替换

我们可以创建一个通用的模板函数,能够处理任意SQL语句中的占位符替换。这个函数将接受两个参数: sqlTemplate:包含占位符的SQL模板字符串。params:一个对象数组,每个对象包含name和value,用于替换SQL模板中的占位符。通用模板函数 function replaceSqlPlaceholders(sqlT…

Fabric.js 中文文档

Fabric.js 中文文档 基于canvas画布的实用类Fabric.js的使用 4、Fabric.js 常用的方法&事件 Fabric.js 画布 defaultCursor 属性(1) 官网文档地址&#xff1a;http://fabricjs.com/docs/github 地址&#xff1a;https://github.com/fabricjs/fabric.js Demo地址&#x…

c++:thread(线程)

1.基本使用 1.1创建线程 join()函数用于&#xff1a;主程序等待子线程执行完毕之后再继续 #include <iostream> #include <thread>void printHello() {std::cout << "hello world" << std::endl; }int main() {// 1.创建线程std::thread …

第六届金盾信安杯-SSRF

操作内容&#xff1a; 进入环境 可以查询网站信息 查询环境url https://114.55.67.167:52263/flag.php 返回 flag 就在这 https://114.55.67.167:52263/flag.php 把这个转换成短连接&#xff0c;然后再提交 得出 flag

Spark优化--开发调优、资源调优、数据倾斜调优和shuffle调优等

针对Spark优化&#xff0c;我们可以从多个角度进行&#xff0c;包括开发调优、资源调优、数据倾斜调优和shuffle调优等。以下是一些具体的优化方法&#xff1a; 1. 开发调优 避免创建重复的RDD&#xff1a;对于同一份数据&#xff0c;只应该创建一个RDD&#xff0c;避免创建多…

PHP和GD库如何调整图片尺寸

PHP和GD库可以通过一系列函数调整图片的尺寸。以下是一个详细的步骤说明&#xff1a; 一、准备工作 检查GD库是否安装&#xff1a; 使用命令php -i | grep -i gd来检查GD库是否已经安装。如果返回类似于“GD Support > enabled”的内容&#xff0c;则表示安装成功。如果没有…

递归算法讲解(c基础)

递归的定义 递归是指在函数的定义中使用函数自身的方法。它是一种解决问题的策略&#xff0c;将一个大型复杂的问题逐步分解为规模更小的、与原问题相似的子问题来解决。当子问题的规模足够小&#xff0c;达到一个可以直接求解的基本情况&#xff08;也称为终止条件&#xff09…

有一个已经排好序的数组。现输入一个数,要求按原来的规律将它插入数组中。-多语言

目录 C 语言实现 Python 实现 Java 实现 Js 实现 题目&#xff1a;有一个已经排好序的数组。现输入一个数&#xff0c;要求按原来的规律将它插入数组中。 程序分析&#xff1a;首先判断此数是否大于最后一个数,然后再考虑插入中间的数的情况,插入后此元素之后的数,依次后移…

SpringMVC(2)

前言 这一节我们终结springmvc 1. SSM整合配置 先导入坐标 先创建包 配置类 然后开始创建jdbc的config和mybatis的config&#xff0c;还有properties SpringConfig&#xff1a; jdbc.properties&#xff1a; JdbcConfig: MybatisConfig: 下面开始spring整合mvc&#…