**注:**在《SVD(奇异值分解)小结 》中分享了SVD原理,但其中只是利用了numpy.linalg.svd函数应用了它,并没有提到如何自己编写代码实现它,在这里,我再分享一下如何自已写一个SVD函数。但是这里会利用到SVD的原理,如果大家还不明白它的原理,可以去看看《SVD(奇异值分解)小结 》,或者自行百度/google。数据集:https://pan.baidu.com/s/1ZmpUSIscy4VltcimwwIWew。

1、SVD算法实现

1.1 SVD原理简单回顾

有一个$m \times n$的实数矩阵$A$,我们可以将它分解成如下的形式

$$ A = U\Sigma V^T \tag{1-1} $$

其中$U$和$V$均为单位正交阵,即有$UU^T=I$和$VV^T=I$,$U$称为左奇异矩阵,$V$称为右奇异矩阵,$\Sigma$仅在主对角线上有值,我们称它为奇异值,其它元素均为0。上面矩阵的维度分别为$U \in \mathbf{R}^{m\times m},\ \Sigma \in \mathbf{R}^{m\times n}$,$\ V \in \mathbf{R}^{n\times n}$。

正常求上面的$U,V,\Sigma$不便于求,我们可以利用如下性质

$$ AA^T=U\Sigma V^TV\Sigma^TU^T=U\Sigma \Sigma^TU^T \tag{1-2} $$ $$ A^TA=V\Sigma^TU^TU\Sigma V^T=V\Sigma^T\Sigma V^T \tag{1-3} $$

1.2 SVD算法

据1.1小节,对式(1-3)和式(1-4)做特征值分解,即可得到奇异值分解的结果。但是样分开求存在一定的问题,由于做特征值分解的时候,特征向量的正负号并不影响结果,比如,我们利用式(1-3)和(1-4)做特征值分解

$$ AA^T\mathbf{u}_i = \sigma_i \mathbf{u}_i\quad \text{or} \quad AA^T(-\mathbf{u}_i) = \sigma_i (-\mathbf{u}_i)\ A^TA\mathbf{v}_i = \sigma_i \mathbf{v}_i\quad \text{or} \quad A^TA(-\mathbf{v}_i) = \sigma_i (-\mathbf{v}_i) $$

如果在计算过程取,取上面的$\mathbf{u}_i$组成左奇异矩阵$U$,取$-\mathbf{v}_i$组成右奇异矩阵$V$,此时$A\ne U\Sigma V^T$。因此求$\mathbf{v}_i$时,要根据$\mathbf{u}_i$来求,这样才能保证$A= U\Sigma V^T$。因此,我们可以得出如下1.1计算SVD的算法。它主要是先做特性值分解,再根据特征值分解得到的左奇异矩阵$U$间接地求出部分的右奇异矩阵$V'\in \mathbf{R}^{m\times n}$。

算法1.1:SVD

输入:样本数据 输出:左奇异矩阵,奇异值矩阵,右奇异矩阵

计算特征值: 特征值分解$AA^T$,其中$A \in \mathbf{R}^{m\times n}$为原始样本数据

$$ AA^T=U\Sigma \Sigma^TU^T $$

得到左奇异矩阵$U \in \mathbf{R}^{m \times m}$和奇异值矩阵$\Sigma' \in \mathbf{R}^{m \times m}$

间接求部分右奇异矩阵: 求$V' \in \mathbf{R}^{m \times n}$

利用$A=U\Sigma'V'$可得

$$ V' = (U\Sigma')^{-1}A = (\Sigma')^{-1}U^TA \tag{1-4} $$

返回$U,\ \Sigma',\ V'$,分别为左奇异矩阵,奇异值矩阵,右奇异矩阵。

**注:**这里得到的$\Sigma'$和$V'$与式(1-2)所得到的$\Sigma,\ V$有区别,它们的维度不一样。$\Sigma'$是只取了前$m$个奇异值形成的对角方阵,即$\Sigma' \in \mathbf{R}^{m \times m}$;$V'$不是一个方阵,它只取了$V \in \mathbf{R}^{m \times n}$的前$m$行(假设$m < n$),即有$V' = V(:m,\cdot)$。这样一来,我们同样有类似式(1-1)的数学关系成立,即 $$ A = U\Sigma' (V')^T\tag{1-5} $$

我们可以利用此关系重建原始数据。

2、SVD的Python实现

以下代码的运行环境为python3.6+jupyter5.4。

2.1 SVD实现过程

读取数据

这里面的数据集大家随便找一个数据就好,如果有需要我的数据集,可以下在面留言。

import numpy as np

import pandas as pd

from scipy.io import loadmat

# 读取数据,使用自己数据集的路径。

train_data_mat = loadmat("../data/train_data2.mat")

train_data = train_data_mat["Data"]

print(train_data.shape)

特征值分解

# 数据必需先转为浮点型,否则在计算的过程中会溢出,导致结果不准确

train_dataFloat = train_data / 255.0

# 计算特征值和特征向量

eval_sigma1,evec_u = np.linalg.eigh(train_dataFloat.dot(train_dataFloat.T))

计算右奇异矩阵

#降序排列后,逆序输出

eval1_sort_idx = np.argsort(eval_sigma1)[::-1]

# 将特征值对应的特征向量也对应排好序

eval_sigma1 = np.sort(eval_sigma1)[::-1]

evec_u = evec_u[:,eval1_sort_idx]

# 计算奇异值矩阵的逆

eval_sigma1 = np.sqrt(eval_sigma1)

eval_sigma1_inv = np.linalg.inv(np.diag(eval_sigma1))

# 计算右奇异矩阵

evec_part_v = eval_sigma1_inv.dot((evec_u.T).dot(train_dataFloat))

上面的计算出的evec_u, eval_sigma1, evec_part_v分别为左奇异矩阵,所有奇异值,右奇异矩阵。

2.2 SVD降维后重建数据

取不同个数的奇异值,重建图片,计算出均方误差,如图2-1所示。从图中可以看出,随着奇异值的增加,均方误差(MSE)在减小,且奇异值和的比率正快速上升,在100维时,奇异值占总和的53%。

图2-1 奇值分解维度和均方误差变化图

注: 均方误差MSE有如下计算公式 $$ \text{MSE} = \frac{1}{n}\left((y_1-y_1')^2+(y_2-y_2')^2+\cdots+(y_n-y_n')^2\right) $$

我们平时听到的$\text{RMSE}=\sqrt{\text{MSE}}$。

将图和10、50、100维的图进行比较,如图2-2所示。在直观上,100维时,能保留较多的信息,此时能从图片中看出车辆形状。

图2-2 原图与降维重建后的图比较

总结

SVD与特征值分解(EVD)非常类似,应该说EVD只是SVD的一种特殊怀况。我们可以通过它们在实际的应用中返过来理解特征值/奇异值的含义:特征值/奇异值代表着数据的信息量,它的值越大,信息越多。

最近作业是真的多呀,冒着生命危险来分享,希望能给大家带来帮助:smile:

python实现奇异值分解_SVD(奇异值分解)Python实现相关推荐

  1. svd奇异值分解_SVD(奇异值分解)到底在干什么

    奇异值分解就是在低维空间中寻找最接近原矩阵 的低维矩阵 ,说白了就是数据降维. 奇异值分解是一种十分重要但又难以理解的矩阵处理技术,据人工智能的大牛吴恩达老师所说,在机器学习中是最重要的分解没有之一的 ...

  2. python调用simulink_[Python-MATLAB] 在Python中调用MATLAB的API

    可以参考官方的说明文档: MATLAB Engine API的使用文档: 原材料: 1.MATLAB 2015a  32位的 2.Python 2.7.13    32位的 安装: 1.运行cmd,切 ...

  3. 面试前赶紧看了5道Python Web面试题,Python面试题No17

    目录 本面试题题库,由公号:非本科程序员 整理发布 第1题: Flask中的请求上下文和应用上下文是什么? 第2题:django中间件的使用? 第3题: django开发中数据做过什么优化? 第4题: ...

  4. python queue 调试_学Python不是盲目的,是有做过功课认真去了解的

    有多少伙伴是因为一句'人生苦短,我用Python'萌生想法学Python的!我跟大家更新过很多Python学习教程普及过多次的Python相关知识,不过大家还是还得计划一下Python学习路线!Pyt ...

  5. linux python版本_linux下更新Python版本并修改默认版本

    linux下更新Python版本并修改默认版本,有需要的朋友可以参考下. 很多情况下拿到的服务器python版本很低,需要自己动手更改默认python版本 1.从官网下载python安装包(这个版本可 ...

  6. Python培训教程分享:Python异常机制

    ​ 在学习Python技术的时候,我们经常会遇到一些异常,例如导致程序在运行过程中出现的中断或退出,我们都称之为异常,大多数的异常都不会被程序处理,而是以错误信息的形式展现出来.本期Python培训教 ...

  7. Python培训教程分享:Python中选择结构是什么

    越来越多的人开始报名学习Python技术,那么学习Python技术不是一两天就能学会的,本期小编为大家推荐的Python培训教程主要讲的是"Python中选择结构是什么",下面来看 ...

  8. Python培训教程分享:Python模块如何导入__all__属性?

    本期小编为大家带来的Python培训教程是关于"Python模块如何导入__all__属性?"的内容,后面在工作中是会遇到Python模块这个工作内容的,Python模块的开头通常 ...

  9. 【python教程入门学习】Python零基础入门爬虫项目

    Python入门爬虫项目 这是我的第一个python项目,分享给大家. 需求 我们目前正在开发一款产品其功能大致是:用户收到短信如:购买了电影票或者火车票机票之类的事件.然后app读取短信,解析短信, ...

  10. Python学习全家桶,Python初学者十一个热门问题

    一.学习Python要用什么系统? Python是跨平台的,什么系统都可以 二.学习Python用什么编辑器? 这里小编推荐pycharm PyCharm带有一整套可以帮助用户在使用Python语言开 ...

最新文章

  1. 震惊!ConcurrentHashMap里面也有死循环,作者留下的“彩蛋”了解一下?
  2. qt 删除文件夹_Qt 贪吃蛇制作(含源码)
  3. python程序运行不出来_python实战演练2:python可执行文件运行不成功怎么办
  4. C#7.0之ref locals and returns (局部变量和引用返回)
  5. windows7官方原版_从零开始学装系统——微软官方原版windows7详细安装流程
  6. python爬虫网页数据案例_python+vue实现网站爬虫数据分析案例
  7. 打造可降级的React服务端同构框架
  8. 让程序最小化到任务栏的时候隐藏
  9. 毕业五年总结(转载的别人帖子,挺励志)
  10. 多项分布(一种离散分布)
  11. python 读写csv文件(创建、追加、覆盖)_python文件操作
  12. 使用cryptsetup加密硬盘
  13. UiPath与按键精灵区别
  14. 全新UI众人帮任务帮PHP源码 悬赏任务抖音快手头条点赞源码 带三级分销可封装小程序
  15. Java笔记-面向对象(上)
  16. WIN7卸载IE11回复IE8的方法
  17. 前端-table表格隔行变色
  18. iOS 开发:彻底理解 iOS 内存管理(MRC 篇)
  19. 盘点2022初级Java笔试题,选择题,简答题(右滑查看答案)
  20. python英汉互译-中汉英在线翻译

热门文章

  1. 一季度全国主要城市交通分析报告 高德发布
  2. 从进化论的角度聊一聊大分子编码说和老王谬论
  3. discuz 如何去掉:导读-最新发表
  4. 基于图像的三维重建——基于空间patch扩散的方法(PMVS)
  5. 足不出户也能放风筝?OpenGL 一招搞定!
  6. canvas画地图运动轨迹【自己定位】
  7. 马克思主义哲学历史唯物主义
  8. 【分享】一年级古诗古朗月行语文知识点心田花开汇总
  9. SnapChat明年IPO 创始人为保证控制权改股权结构
  10. HDU 1814(染色)